Bulk Insert Failed Ошибка преобразования данных массовой загрузки (усечение)

Я выполнял импорт данных с помощью задачи SQL Server BULK INSERT сотни раз, но на этот раз я получаю незнакомую ошибку, которую я безуспешно пытался устранить с помощью Google. Ниже приведен код, который я использую с файлом, разделенным запятыми, где новые строки обозначаются символами новой строки:

BULK INSERT MyTable
FROM 'C:\myflatfile.txt'
WITH (
    FIELDTERMINATOR = ','
    ,ROWTERMINATOR = '/n')
GO

Он стабильно работает, но теперь в простом файле с датой и скоростью происходит сбой с ошибкой «Сообщение 4863, уровень 16, состояние 1, строка 1 Ошибка преобразования данных массовой загрузки (усечение) для строки 1, столбца 2 (столбец два)." Когда я смотрю на файл, я не понимаю, почему это может привести к сбою (обычно поиск и устранение неполадок Google указывает, что разделители могут существовать несколько раз в строке, что может вызвать эту ошибку). Вот первые десять строк из файла (обратите внимание, что в ПЕРВОЙ строке происходит сбой):

1961-01-01,8.2
1961-02-01,8.2
1961-03-01,7.4
1961-04-01,7.6
1961-05-01,7.8
1961-06-01,8.5
1961-07-01,9.1
1961-08-01,8.8
1961-09-01,8.4
1961-10-01,8.8

Таблица, в которую я вставляю эти данные, имеет два поля: VARCHAR(50), хотя, когда я впервые увидел усечение, я расширил поля данных до VARCHAR(2000), и это не повлияло на это.

CREATE TABLE MyTable (
    ColumnOne VARCHAR(50),
    ColumnTwo VARCHAR(50)
)

Я также попытался удалить все тире, чтобы увидеть, не испортит ли это ситуацию (хотя я сделал много импортов данных с тире, используя тот же код, и он работает без ошибок), и все равно получил то же сообщение об ошибке.

Прямой импорт работает (через Tasks), как и SSIS, но как насчет того, чтобы этот код дал сбой, ведь он должен делать то же самое?


person Tim    schedule 01.03.2013    source источник


Ответы (2)


Проблема, скорее всего, в том, что разделитель строк не работает из-за формата файла.

Пытаться:

ROWTERMINATOR = '0x0a'

РЕДАКТИРОВАТЬ

На самом деле я просто заметил, что вы используете косую черту, это должна быть обратная косая черта, так что это может сработать:

ROWTERMINATOR = '\n'
person EkoostikMartin    schedule 01.03.2013
comment
Спасибо; как я могу различить, является ли это «/ n» или «0x0a», так как в файле он выглядит как символ новой строки? Я не видел этот до этого. - person Tim; 01.03.2013
comment
Если ваш файл находится в системе на базе UNIX, вы должны обычно использовать «0x0a» (поскольку UNIX использует только \n - перевод строки в качестве терминатора). Если ваш файл из Windows, массовое копирование будет фактически использовать \r\n, даже если вы укажете только \n (что является одновременно возвратом каретки и переводом строки). - person EkoostikMartin; 01.03.2013

Из SQL Server Management Studio (SSMS) для файла в стиле Unix работает ROWTERMINATOR = '0x0a'. Однако ROWTERMINATOR = '\n' не работает, поскольку SSMS, по-видимому, интерпретирует \n как последовательность конца строки в стиле Windows (\r\n) и исправляет/разбивает ее для вас.

Интересно, что если вы отправите тот же ROWTERMINATOR = '\n' из кода Java через драйвер JDBC SQL Server, он будет рассматриваться как конец строки в стиле Unix, поскольку ничто в середине не добавляет дополнительный \r.

Итак, вам нужно сделать две вещи:

1 - Убедитесь, что вы понимаете, как ваш файл данных на самом деле работает в конце строки.

2. Убедитесь, что вы понимаете, как ваши средства доставки BULK INSERT sql на SQL Server интерпретируют любые escape-последовательности. Мой ограниченный опыт заключается в том, что использование шестнадцатеричного ('0x0a') для SQL Server SQL работает во всех средах.

person DocOc    schedule 16.04.2016