Определить ROW, вызвавшую ошибку «неожиданный конец файла» в BULK INSERT?

17

Я делаю объемную вставку:

DECLARE @row_terminator CHAR;
SET @row_terminator = CHAR(10); -- or char(10)

DECLARE @stmt NVARCHAR(2000);
SET @stmt = '
  BULK INSERT accn_errors
   FROM ''F:\FullUnzipped\accn_errors_201205080105.txt''
   WITH 
      (
        firstrow=2,
FIELDTERMINATOR = ''|''  ,
ROWS_PER_BATCH=10000
   ,ROWTERMINATOR='''+@row_terminator+'''
   )'
exec sp_executesql @stmt;

, и я получаю следующую ошибку:

Msg 4832, Level 16, State 1, Line 2
Bulk load: An unexpected end of file was encountered in the data file.
Msg 7399, Level 16, State 1, Line 2
The OLE DB provider "BULK" for linked server "(null)" reported an error. The provider did not give any information about the error.
Msg 7330, Level 16, State 2, Line 2
Cannot fetch a row from OLE DB provider "BULK" for linked server "(null)".

Есть ли способ узнать, на какой ROW произошла эта ошибка?

Я могу импортировать 10 000 000 строк без проблем, и после этого возникает ошибка

    
задан l--''''''---------'''''''''''' 08.05.2012 в 23:57
источник

10 ответов

38

Чтобы найти трудную строку, используйте спецификатор файла ошибок.

BULK INSERT myData
FROM 'C:\...\...\myData.csv'
WITH (
FIELDTERMINATOR = ',',
ROWTERMINATOR = '\n',
ERRORFILE = 'C:\...\...\myRubbishData.log' 
);

myRubbishData.log будет иметь оскорбительные строки и файл-компаньон myRubbishData.log.txt предоставит вам номера строк и смещения в файл.

Пример файла компаньона:

Row 3 File Offset 152 ErrorFile Offset 0 - HRESULT 0x80004005
Row 5 File Offset 268 ErrorFile Offset 60 - HRESULT 0x80004005
Row 7 File Offset 384 ErrorFile Offset 120 - HRESULT 0x80004005
Row 10 File Offset 600 ErrorFile Offset 180 - HRESULT 0x80004005
Row 12 File Offset 827 ErrorFile Offset 301 - HRESULT 0x80004005
Row 13 File Offset 942 ErrorFile Offset 416 - HRESULT 0x80004005
    
ответ дан user1588622 29.10.2012 в 21:29
источник
3

У меня есть файл csv, который я импортирую с помощью Bulk

BULK INSERT [Dashboard].[dbo].[3G_Volume]
FROM 'C:G_Volume.csv'
WITH
(
FIRSTROW = 2,
FIELDTERMINATOR = '","',
ROWTERMINATOR = '\n'
)
GO

Обычно я использовал этот скрипт, и у него нет проблем, но в редких случаях.

Я сталкиваюсь с этой ошибкой.

"Поставщик OLE DB« BULK »для связанного сервера« (null) »сообщил об ошибке. Поставщик не предоставил никакой информации об ошибке.

Обычно это происходит, когда последняя строка имеет пустые значения (null).

Вам нужно связать свой файл csv в MS access db, чтобы проверить данные. (Если ваш csv не превышает 1,4 миллиона строк, вы можете открыть его в excel)

Поскольку мои данные составляют около 3 миллионов строк, мне нужно использовать db доступа.

Затем проверьте номер последней строки с пробелами и вычтите количество нулевых строк для ваших общих строк для csv.

, если у вас есть 2 пустых строки в конце, а общее количество строк - 30000005 Сценарий станет таким.

BULK
INSERT [Dashboard].[dbo].[3G_Volume]
 FROM 'C:G_Volume.csv'
WITH
(
FIRSTROW = 2,
FIELDTERMINATOR = '","',
ROWTERMINATOR = '\n',
Lastrow = 30000003
)
GO

Приветствия ... Mhelboy

    
ответ дан Mhelboy 28.10.2015 в 21:48
источник
2

Весело, весело, весело. Я не нашел хороший способ отладить эти проблемы, поэтому я использую грубую силу. То есть параметры FirstRow и LastRow очень полезны.

Начните с LastRow = 2 и продолжайте попытки. Загрузите результаты в таблицу сбрасывания, которую вы можете легко урезать.

И вы также должны помнить, что первая строка также может вызывать проблемы.

    
ответ дан Gordon Linoff 09.05.2012 в 00:19
источник
2

Если CHAR (10) является ограничителем строк, я не думаю, что вы можете поместить его в кавычки, как вы пытаетесь в BULK INSERT. Существует недокументированный способ указать это:

ROWTERMINATOR = '0x0A'
    
ответ дан Steve Kass 09.05.2012 в 02:51
источник
1

Да - BULK INSERT сделал бы это с более подробной информацией в сообщениях об ошибках, и единственный способ этого - использовать подход грубой силы, как справедливо указал Гордон. Во-первых, однако, исходя из ошибки, которую вы получаете, это либо не понимает ваш терминатор строк, либо в конце файла отсутствует ограничитель строк. Использование FIRSTROW и LASTROW поможет определить это.

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

  1. Убедитесь, что в конце файла есть терминатор строки. Если нет, введите один и повторите попытку. Также убедитесь, что последняя строка содержит все необходимые поля. Это говорит «EOF», тогда это ваша проблема.
  2. Вы уверены, что есть LF в конце каждой строки? Попробуйте CR (\ n, 0x0D) и посмотрите, работает ли это.
  3. Все еще не работает? Попробуйте установить LASTROW = 2 и повторите попытку. Затем попробуйте LASTROW = 3. Если у вас более трех строк в вашем файле, и этот шаг завершается неудачно, то терминатор строки не работает.
ответ дан Peter 09.05.2012 в 09:36
источник
1

Я столкнулся с той же проблемой. Я написал сценарий оболочки для создания CSV в Linux. Я взял это .csv в Windows и попытался навалом загрузить данные. Он не «любил» запятые ... Не спрашивайте меня, почему, но я изменил на * в качестве разделителя в массовом импорте и выполнил поиск и заменил запятую * на моем .csv .., который работал .. Я изменился на ~ как разделитель, который работал ... вкладка тоже работала - ему не нравилась запятая ... Надеюсь, это кому-то поможет.     

ответ дан user2125311 07.03.2013 в 15:31
источник
0

По моему опыту это почти всегда вызвано чем-то в последних двух строках. tail файла импорта, и он все равно должен дать вам сбой. Затем откройте его в полнотекстовом редакторе, который позволит вам увидеть непечатаемые символы, такие как CR, LF и EOF. Это должно позволить вам заманить его в работу, даже если вы не знаете, почему. Например, BULK INSERT терпит неудачу с терминатором строки в последней строке

    
ответ дан feetwet 13.08.2014 в 21:18
источник
0

У меня возникла проблема, преобразовывая все поля в строки и затем используя общий FIELDTERMINATOR. Это сработало:

BULK INSERT [dbo].[workingBulkInsert]  
FROM 'C:\Data\myfile.txt' WITH (
   ROWTERMINATOR = '\n', 
   FIELDTERMINATOR = ',' 
)

Теперь мой файл данных выглядит следующим образом:

"01502","1470"
"01504","686"
"02167","882"
"106354","882"
"106355","784"
"106872","784"

Второе поле было десятичным типом без разделителя с двойной кавычкой (например, 1470,00). Форматирование как в виде строк устраняет ошибку.

    
ответ дан Karl Hoaglund 05.07.2016 в 19:04
источник
-1

У меня возникла проблема, если я преобразовал все поля в строку и затем использовал общий разделитель полей.

    
ответ дан Karl Hoaglund 05.07.2016 в 18:52
источник
-3

строки, генерирующие эту ошибку, не имеют CHAR(10) терминатора или имеют ненужные пробелы

    
ответ дан stefano 14.11.2014 в 00:35
источник