Причина:
Служба SSIS не может прочитать файл и отображает следующее предупреждение из-за разделителя столбцов Ç
( "c" с cedilla ) и not
из-за ограничителя строки {LF}
( перевод строки ).
[Read flat file [1]] Warning: The end of the data file was reached while
reading header rows. Make sure the header row delimiter and the number of
header rows to skip are correct.
Вот пример пакета служб SSIS, в котором показано, как решить проблему с помощью Script Component
, а в конце - еще один пример, имитирующий вашу проблему.
Разрешение:
Ниже образец пакета написан в SSIS 2008 R2
. Он читает плоский файл с разделителем строк {LF}
в виде значения одного столбца; затем разделяет данные, используя Script Component
, чтобы вставить информацию в таблицу в базе данных SQL Server 2008 R2
.
Используйте Блокнот ++ , чтобы создать простой плоский файл с несколькими строками. В приведенном ниже примере файла Идентификатор продукта и Прайс-лист информация о каждой строке разделена Ç
как разделитель столбцов, и каждая строка заканчивается {LF}
разделитель.
В Блокноте ++ нажмите Encoding
, а затем нажмите Encoding in UTF-8
, чтобы сохранить плоский файл в кодировке UTF-8
.
В примере будет использоваться база данных SQL Server 2008 R2
с именем Sora
. Создайте новую таблицу с именем dbo.ProductListPrice
, используя приведенный ниже скрипт. Служба SSIS вставит данные плоского файла в эту таблицу.
USE Sora;
GO
CREATE TABLE dbo.ProductListPrice
(
ProductId nvarchar(30) NOT NULL
, ListPrice numeric(12,2) NOT NULL
);
GO
Создание пакета служб SSIS с использованием Business Intelligence Development Studio (BIDS) 2008 R2 . Назовите пакет как SO_6268205.dtsx
. Создайте источник данных с именем Sora.ds
для подключения к базе данных Sora
в SQL Server 2008 R2 .
Щелкните правой кнопкой мыши в любом месте внутри пакета и затем нажмите Variables
, чтобы просмотреть панель переменных. Создайте новую переменную с именем ColumnDelimiter
типа данных String
в области действия пакета SO_6268205
и установите переменную со значением Ç
Щелкните правой кнопкой мыши на Connection Managers
и выберите New Flat File Connection...
, чтобы создать соединение для чтения плоского файла.
На странице General
редактора диспетчера соединений с плоскими файлами выполните следующие действия:
- Установить Имя диспетчера соединений в
ProductListPrice
- Набор Описание до
Flat file connection manager to read product list price information.
- Выберите путь к плоскому файлу. У меня есть файл в пути
C:\Siva\StackOverflow\Files\6268205\ProductListPrice.txt
- Выберите
{LF}
из Разделитель строк заголовка
- Проверка
Column names in the first data row
- Нажмите
Columns
Страница
На странице Columns
редактора диспетчера соединений с плоскими файлами убедитесь, что Column delimiter
пусто и отключено. Нажмите Advanced
страницу.
На странице Advanced
редактора диспетчера соединений с плоскими файлами выполните следующие действия.
- Установите Имя на
LineData
- Убедитесь, что разделитель столбцов установлен на
{LF}
- Установите Тип данных на
Unicode string [DT_WSTR]
- Установите OutputColumnWidth в
255
- Нажмите на страницу
Preview
.
На странице Preview
редактора диспетчера соединений с плоскими файлами убедитесь, что отображаемые данные выглядят правильно, и нажмите OK
.
Вы увидите источник данных Sora и менеджер соединений с плоскими файлами ProductListPrice на вкладке Connection Managers
в нижней части пакета.
Перетащите Data Flow Task
на вкладку Control Flow пакета и назовите ее File to database - Without Cedilla delimiter
Дважды щелкните по задаче Поток данных , чтобы переключить представление на вкладку Data Flow
в пакете. Перетащите Flat File Source
на вкладку Поток данных . Дважды щелкните Источник плоских файлов , чтобы открыть Flat File Source Editor
.
На странице Connection Manager
редактора источника плоских файлов выберите Диспетчер соединений с плоскими файлами ProductListPrice
и нажмите Столбцы стр.
На странице Columns
редактора Источник плоских файлов проверьте столбец LineData
и нажмите OK
.
Перетащите Script Component
на вкладку Поток данных под Источник плоских файлов , выберите Transformation
и нажмите OK
. Подключите зеленую стрелку от Источник плоского файла к Компонент сценария . Дважды щелкните Компонент скрипта , чтобы открыть Script Transformation Editor
.
Нажмите Входные столбцы на Редактор преобразования сценариев и выберите LineData
столбец. Нажмите Входы и выходы Страница.
На странице Inputs and Outputs
редактора преобразования сценариев выполните следующие действия.
- Измените имя входа на FlatFileInput
- Измените имя выходов на
SplitDataOutput
- Выберите Выходные столбцы и нажмите
Add Column
. Повторите это снова, чтобы добавить еще один столбец.
- Назовите первый столбец
ProductId
- Установите DataType столбца ProductId в
Unicode string [DT_WSTR]
- Установите Длина в
30
На странице Inputs and Outputs
редактора преобразования сценариев выполните следующие действия.
- Назовите второй столбец
ListPrice
- Установите DataType столбца ListPrice в
numeric [DT_NUMERIC]
- Установите Точность на
12
- Установите Шкала на
2
- Нажмите Страница сценария , чтобы изменить сценарий
На странице Script
редактора преобразования сценариев выполните следующие действия.
- Нажмите кнопку с многоточием напротив ReadOnlyVariables и выберите переменную
User::ColumnDelimiter
- Нажмите
Edit Script...
Вставьте приведенный ниже C # в Редактор скриптов. Скрипт выполняет следующие задачи.
- Используя значение разделителя столбцов
Ç
, определенное в переменной User :: ColumnDelimiter , метод FlatFileInput_ProcessInputRow
разбивает входящее значение и присваивает его в два выходных столбца, определенных в преобразовании компонента сценария.
Код компонента сценария на C #
using System;
using System.Data;
using Microsoft.SqlServer.Dts.Pipeline.Wrapper;
using Microsoft.SqlServer.Dts.Runtime.Wrapper;
[Microsoft.SqlServer.Dts.Pipeline.SSISScriptComponentEntryPointAttribute]
public class ScriptMain : UserComponent
{
public override void PreExecute()
{
base.PreExecute();
}
public override void PostExecute()
{
base.PostExecute();
}
public override void FlatFileInput_ProcessInputRow(FlatFileInputBuffer Row)
{
const int COL_PRODUCT = 0;
const int COL_PRICE = 1;
char delimiter = Convert.ToChar(this.Variables.ColumnDelimiter);
string[] lineData = Row.LineData.ToString().Split(delimiter);
Row.ProductId = String.IsNullOrEmpty(lineData[COL_PRODUCT])
? String.Empty
: lineData[COL_PRODUCT];
Row.ListPrice = String.IsNullOrEmpty(lineData[COL_PRICE])
? 0
: Convert.ToDecimal(lineData[COL_PRICE]);
}
}
Перетащите OLE DB Destination
на вкладку Поток данных . Подключите зеленую стрелку от Компонент сценария к Назначение OLE DB . Дважды щелкните OLE DB Destination , чтобы открыть OLE DB Destination Editor
.
На странице Connection Manager
редактора адресатов OLE DB выполните следующие действия.
- Выберите
Sora
из Диспетчер соединений OLE DB
- Выберите
Table or view - fast load
из Режим доступа к данным
- Выберите
[dbo].[ProductListPrice]
из Имя таблицы или представления
- Нажмите Отображения Страница
Нажмите Mappings
на странице Редактор адресатов OLE DB автоматически сопоставит столбцы, если имена входных и выходных столбцов совпадают. Нажмите OK
.
Поток данных * Вкладка 1548 * должна выглядеть примерно так после настройки всех компонентов.
Выполнить запрос select * from dbo.ProductListPrice
в SQLServer Management Studio (SSMS) , чтобы найти количество строк в таблице.Он должен быть пустым перед выполнением пакета.
Выполнить пакет.Вы заметите, что пакет успешно обработал 9 строк.Плоский файл содержит 10 строк, но первая строка представляет собой заголовок с именами столбцов.
Выполните запрос select * from dbo.ProductListPrice
на SQL ServerManagement Studio (SSMS) для поиска строк 9 , успешно вставленных в таблицу.Данные должны совпадать с данными плоского файла.
В приведенном выше примере показано, как вручную разбивать данные с помощью Script Component , поскольку Flat FileДиспетчер подключений обнаруживает ошибку при настройке разделителя столбцов Ç
Имитация проблемы:
В этом примере показан отдельный Диспетчер соединений с плоскими файлами настроен с разделителем столбцов Ç
, который выполняется, но встречает предупреждение и не обрабатывает никаких строк.
Щелкните правой кнопкой мыши на Connection Managers
и выберитеNew Flat File Connection...
для создания соединения для чтения плоского файла.На странице General
редактора диспетчера соединений с плоскими файлами выполните следующие действия:
- Задать Имя диспетчера соединений
ProductListPrice_Cedilla
- Установить описание на
Flat file connection manager with Cedilla column delimiter.
- У меня есть файл в пути
C:\Siva\StackOverflow\Files\6268205\ProductListPrice.txt
Выберите плоский путь к файлу. - Выберите
{LF}
из Разделитель строк заголовка - Проверка
Column names in the first data row
- Нажмите
Columns
страница
На странице Columns
редактора диспетчера соединений с плоскими файлами , выполните следующие действия:
- Установите Разделитель строк на
{LF}
- Поле разделителя столбцов может быть отключено.Нажмите
Reset Columns
- Установите Разделитель столбцов на
Ç
- Нажмите
Advanced
page
На странице Advanced
редактора диспетчера соединений с плоскими файлами выполните следующие действия:
- Установите Имя на
ProductId
- Установите ColumnDelimiter на
Ç
- Установите DataType на
Unicode string [DT_WSTR]
- Установите Длина на
30
- Щелкните столбец
ListPrice
На странице Advanced
Редактор диспетчера соединений с плоскими файлами , выполните следующие действия:
- Установите Имя на
ListPrice
- Установите ColumnDelimiter до
{LF}
- Установите DataType на
numeric [DT_NUMERIC]
- Установите Точность данных до
12
- Установите DataScale на
2
- Нажмите
OK
Перетащите Data Flow task
на вкладку Control Flow и назовите его File to database - With Cedilla delimiter
.Отключите первую задачу потока данных.
Настройте вторую задачу потока данных с Flat File Source
и OLE DB Destination
Дважды щелкните Источник плоского файла, чтобы открыть Flat File Source Editor
.На странице Connection Manager
редактора источника плоских файлов выберите Диспетчер соединений с плоскими файлами ProductListPrice_Cedilla
и нажмите Столбцы настроить столбцы.Нажмите OK
.
Выполнить пакет.Все компоненты будут отображаться зеленым цветом, чтобы указать, что процесс прошел успешно, но строки не будут обработаны.Вы можете видеть, что между Flat File Source
и OLE DB Destination
нет никаких указаний Progress
вкладка, и вы увидите следующее предупреждающее сообщение.
[Read flat file [1]] Warning: The end of the data file was reached while
reading header rows. Make sure the header row delimiter and the number of
header rows to skip are correct.