2010-03-24 6 views
9

Mam ADO.NET DataTable z około 100 000 rekordów. W tej tabeli znajduje się kolumna xyID, która nie zawiera żadnych wartości, ponieważ kolumna jest automatycznie generowana IDENTITY w mojej bazie danych programu SQL Server.Jak uzyskać identyfikatory wstawionych rekordów danych za pomocą SQL bulk copy

Potrzebuję pobrać wygenerowane identyfikatory dla innych procesów. Szukam sposobu, aby zbiorczo skopiować ten DataTable do bazy danych SQL Server, i w tym samym "kroku", aby "wypełnić" mój DataTable z generowanych identyfikatorów.

Jak mogę pobrać wartości tożsamości rekordów wstawionych do tabeli przy użyciu klasy SqlBulkCopy?

Odpowiedz

2

Jestem obecnie robi coś takiego:

DataTable objects = new DataTable(); 
DataColumn keyColumn = new DataColumn("name", typeof(string)); 
DataColumn versionColumn = new DataColumn("version", typeof(int)); 
versionColumn.DefaultValue = iVersionID; 

objects.Columns.Add(keyColumn); 
objects.Columns.Add(versionColumn); 

foreach (KeyValuePair<string, NamedObject> kvp in Directory) 
{ 
    NamedObject o = kvp.Value; 
    DataRow row = objects.NewRow(); 
    row[0] = o.Name; 
    objects.Rows.Add(row); 
} 

using (SqlBulkCopy updater = new SqlBulkCopy(conn, 
     SqlBulkCopyOptions.TableLock | SqlBulkCopyOptions.UseInternalTransaction, null)) 
{ 
    updater.DestinationTableName = "object_table"; 
    updater.WriteToServer(objects); 
} 

string sQuery = @"SELECT id, name FROM object_table WHERE version = @ver"; 
using (SqlCommand command = new SqlCommand(sQuery, conn)) 
{ 
    SqlParameter version = new SqlParameter("@ver", SqlDbType.Int, 4); 
    version.Value = versionID; 
    command.Parameters.Add(version); 

    command.CommandTimeout = 600; 

    using (SqlDataReader reader = command.ExecuteReader()) 
    { 
     while (reader.Read()) 
     { 
      string key = (string)reader[1]; 

      NamedObject item = Directory[key]; 
      item.ID = (int)reader[0]; 
     } 
    } 
} 

pamiętać, że nasz projekt danych umożliwia filtrowanie dla wszystkich naszych nowych obiektów za pomocą identyfikatora wersji; każdy dodawany wiersz będzie miał ten sam identyfikator wersji, a my wcześniej usunęliśmy wszystkie wiersze w bazie danych, które już posiadały ten identyfikator wersji.

Jednak moje zapytanie wybierające ma obecnie limit czasu w ExecuteReader, nawet w tym 10-minutowym oknie. To nie jest nasze ostateczne rozwiązanie.

+0

W rzeczywistości zatrzymaliśmy to rozwiązanie, rozwiązując problemy z przekroczeniem limitu czasu, konfigurując proces wygasania starych i nieistotnych danych. Dodałem kolumnę znacznika czasu i kolumnę "keep" do tabeli wersji i dodałem tryb, który usuwa wszystkie dane powiązane z wersjami starszymi niż miesiąc bez flagi "keep". Nasze problemy z przekroczeniem limitu czasu zniknęły po usunięciu ~ 100 milionów wierszy. – Timbo

Powiązane problemy