2011-02-03 21 views
16

Necesito actualizar periódicamente una tabla muy grande y SQLBulkCopy es perfecto para eso, solo que tengo un índice de 2 columnas que evita los duplicados. ¿Hay alguna forma de utilizar SQLBulkCopy como "insertar o actualizar si existe"?Cualquier forma de SQLBulkCopy "insertar o actualizar si existe"?

Si no, ¿cuál es la forma más eficiente de hacerlo? Nuevamente, estoy hablando de una tabla con millones de registros.

Gracias

Respuesta

8

No en un solo paso, pero en SQL Server , usted podría: carga

  • a granel en la tabla de etapas
  • solicitar una declaración MERGE para actualizar/insertar en su mesa real

Lea más sobre MERGE statement

0

Otra alternativa sería no utilizar un tabla temporal, pero use un procedimiento almacenado con un parámetro valorado de tabla. Pase una tabla de datos a la sp y realice la combinación allí.

5

En lugar de crear una nueva tabla temporal, que BTW consume más espacio y memoria.

Creé un disparador con INSTEAD OF INSERT y uso dentro de la instrucción MERGE.

Pero no olvide agregar el parámetro SqlBulkCopyOptions.FireTriggers en SqlBulkCopy.

Estos son mis dos centavos.

5

Publiqué un paquete nuget (SqlBulkTools) para resolver este problema.

Aquí hay un ejemplo de código que lograría una inserción masiva.

var bulk = new BulkOperations(); 
var books = GetBooks(); 

using (TransactionScope trans = new TransactionScope()) 
{ 
    using (SqlConnection conn = new SqlConnection(ConfigurationManager 
    .ConnectionStrings["SqlBulkToolsTest"].ConnectionString)) 
    { 
     bulk.Setup<Book>() 
      .ForCollection(books) 
      .WithTable("Books") 
      .AddAllColumns() 
      .BulkInsertOrUpdate() 
      .MatchTargetOn(x => x.ISBN) 
      .Commit(conn); 
    } 

    trans.Complete(); 
} 

Para tablas muy grandes, hay opciones para agregar bloqueos de tabla y desactivar temporalmente los índices no agrupados. Ver SqlBulkTools Documentation para más ejemplos.

+0

funciona como un encanto, muchas gracias :) –

+0

Tengo que decir que esta biblioteca está repleta de bondad. Tuve que escribir un servicio de Windows que hizo un trabajo de ETL y la interacción de la base de datos no fue suficiente para justificar incluso un MicroORM y esta biblioteca SqlBulkTools era perfecta. ¡Gracias!. ¡Buen trabajo! – Hallmanac

+1

El enlace de documentación está muerto (404). –

Cuestiones relacionadas