Высокопроизводительная архитектура для сценария импорта данных? - PullRequest
0 голосов
/ 09 февраля 2012

У меня есть сценарий, в котором данные должны быть импортированы из файла CSV через приложение .NET в SQL Server 2008 на сервере базы данных (распределенном).Файл CSV содержит около 4 миллиона «записей» , тогда как таблица назначения может содержать более 100 миллионов записей .Импортируемые данные должны быть проверены на наличие дубликатов существующих данных перед выполнением вставки.

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

Какой подход подходит для этого сценария?

  • Данные для импорта (importdata) необходимо отправить на SQL Server
  • importdataнеобходимо проверить существующие данные (existing) на наличие дубликатов
  • , если в * 1019 обнаружен только один дубликат *, весь импорт для importdata необходимо прервать

Формат CSV

"Name1", "11111111-1111-1111-1111-111111111111"
"Name1", "11111111-1111-1111-1111-111111111111"
"Name1", "11111111-1111-1111-1111-111111111111"

Данные для импорта (схематично в формате DataTable):

Table (
    name nvarchar(20),
    someId uniqueidentifier
)

Таблица назначения на SQL Server(схематично):

Table (
    id int primarykey,
    name nvarchar(20),
    someId uniqueidentifier
)

Ответы [ 3 ]

1 голос
/ 09 февраля 2012

Что бы я сделал.,.

  1. Используя класс SqlBulkCopy, я бы вставил 4 миллиона строк в базу данных во временную таблицу (или таблицу, которая является постоянной, но используется только для этой цели).
  2. ЗаписьProc, который запускает одну таблицу по отношению к другой и только соответствующим образом вставляет строки в таблицу назначения.

Класс SqlBulkCopy, безусловно, является самым быстрым способом получения данных в БД MS SQL, а затем полученияДБ, чтобы сделать обновление, это то, что он хорош.

Обновление Можно ли это сделать в транзакции?

Да, но я бы не хотел представитьтранзакция, охватывающая вставку 4 миллионов строк и обновление других 4 миллионов строк.

Если вы используете временную таблицу истинно (например, #MyTempStrore), тогда временная таблица будет удалена, когда вызавершите этот сеанс в базе данных (например, dbConn.Close()).
Если вы используете таблицу разрешений, вы можете создать уникальный идентификатор сеанса, вставить все строки с этим идентификатором и передать этот идентификатор в хранимый процесс.Затем вы можете удалить эти идентификаторы из таблицы, когда захотите (или просто обрезать таблицу).

Надеюсь, это поможет.

1 голос
/ 09 февраля 2012

Я бы сначала создал временную таблицу для массового импорта всех записей CSV:

BULK
INSERT CSVTEMP
FROM 'c:\csvfile.txt'
WITH
(
FIELDTERMINATOR = ',',
ROWTERMINATOR = '\n'
)
GO

Затем создал бы хранимую процедуру для вставки из CSVTEMP в пункт назначения, выполняя все проверки.

0 голосов
/ 10 февраля 2012

проверьте SQLBulkCopy и SqlBulkCopyOptions.CheckConstraints.Вы можете использовать SQLBulkCopy непосредственно для целевой таблицы и позволить ей откатывать все изменения в случае дублирования ключа.

...