bcp выдает неожиданную ошибку EOF, если в файле нет дополнительного \n

Я импортирую текстовый файл с разделителями табуляции в SQL Server 2012 через BCP. Он работает, за исключением последней строки файла, которая не импортируется. Это не обычная неожиданная проблема EOF, когда разделители установлены неправильно или в данных существует запятая с использованием разделителя-запятой. Разделитель полей явно установлен на \t, а разделитель строк явно установлен на \n. При проверке последней строки в Notepad ++ она правильно содержит данные и символы табуляции. Однако он не имеет разделителя конца строки. Вместо этого файл просто останавливается с последним символом табуляции (последнее поле строки равно нулю). Что, насколько мне известно, нормально.

Странная часть заключается в том, что если я добавлю разделитель конца строки в конец файла, последняя строка импортируется правильно. Единственная необычная вещь в последней строке заключается в том, что данные для первого поля содержат обратную кавычку перед фактическими символьными данными. Но обратные кавычки не используются в качестве разделителей, так что это вряд ли будет проблемой, тем более что строка импортируется, когда я добавляю «дополнительный» разделитель в конце строки.

Итак, должен ли текстовый файл с разделителями всегда иметь разделитель конца строки в конце данных? Или здесь что-то еще происходит?

Анонимный код BCP:

bcp DATABASENAME.dbo.tablename in "L:\directoryname\filename.txt" -c  -S servername -U username -P passwordtext -F 2 -t \t -r \n

person Rominus    schedule 15.08.2017    source источник
comment
1 Да, 2 Нет.   -  person TT.    schedule 15.08.2017


Ответы (1)


Как отметил @TT, вы подозреваете проблему. Одним из решений может быть использование PowerShell для обеспечения закрытия CR/LF в файле:

powershell "Get-Content -Path .\original.tsv | Set-Content -Path .\corrected.tsv;"

Если он есть, он все еще будет там, и новый не будет добавлен. Если он отсутствует, он будет добавлен.

Затем измените свою строку BCP, чтобы использовать исправленное имя файла для ввода, и очистите после себя, как обычно.

person Steven K. Mariner    schedule 15.08.2017
comment
Эта команда powershell добавляет новую строку в конец файла? - person TT.; 15.08.2017
comment
Краткий ответ: Да. Это своего рода побочный эффект. Get-Content читает файл и читает последнюю строку, даже если в ней нет новой строки. Set-Content записывает новый файл и обеспечивает новую строку после каждой записанной строки. Следовательно, если раньше его не было, то теперь есть; и если он был раньше... он все еще там, и новых не добавлялось. - person Steven K. Mariner; 16.08.2017
comment
Бинарная проверка конца файла с добавлением исправлений по мере необходимости была бы более масштабируемым решением, но его проще написать и он подходит как минимум для 80% вероятных сценариев. - person Steven K. Mariner; 16.08.2017