Mamy już uruchomić system, który obsługuje wszystkie ciągi połączeniowy (DB2, oracle, MSServer).Milion wkładki: SqlBulkCopy Timeout
Obecnie używamy ExecuteNonQuery()
do wykonania niektórych przekładek.
Chcemy poprawić wydajność, używając SqlBulkCopy()
zamiast ExecuteNonQuery()
. Mamy kilku klientów, którzy mają ponad 50 milionów rekordów.
Nie chcemy używać SSIS, ponieważ nasz system obsługuje wiele baz danych.
Utworzono przykładowy projekt, aby przetestować wydajność SqlBulkCopy()
. Stworzyłem prostą funkcję odczytu i wstawić do MSServer
Oto mała funkcja:
public void insertIntoSQLServer()
{
using (SqlConnection SourceConnection = new SqlConnection(_sourceConnectionString))
{
//Open the connection to get the data from the source table
SourceConnection.Open();
using (SqlCommand command = new SqlCommand("select * from " + _sourceSchemaName + "." + _sourceTableName + ";", SourceConnection))
{
//Read from the source table
command.CommandTimeout = 2400;
SqlDataReader reader = command.ExecuteReader();
using (SqlConnection DestinationConnection = new SqlConnection(_destinationConnectionString))
{
DestinationConnection.Open();
//Clean the destination table
new SqlCommand("delete from " + _destinationSchemaName + "." + _destinationTableName + ";", DestinationConnection).ExecuteNonQuery();
using (SqlBulkCopy bc = new SqlBulkCopy(DestinationConnection))
{
bc.DestinationTableName = string.Format("[{0}].[{1}]", _destinationSchemaName, _destinationTableName);
bc.NotifyAfter = 10000;
//bc.SqlRowsCopied += bc_SqlRowsCopied;
bc.WriteToServer(reader);
}
}
}
}
}
Kiedy mam mniej niż 200 000 w moim dummyTable kopia większość pracuje bez zarzutu. Ale gdy jest to ponad 200 000 rekordów, mam następujące błędy:
- Próba wywołania masowego kopiowania obiektu, który ma oczekującą operację.
lub
- Operacja oczekiwania limit czasu (na IDataReader)
że zwiększyła CommandTimeout dla czytelnika. Wygląda na to, że rozwiązał problem limitu czasu związanego z IDataReader.
Czy robię coś nie tak w kodzie?
Nigdy nie SqlBulkCopy do tabeli docelowej. To coś poważnie złamało kod blokujący. Zwłaszcza przy użyciu wielowątkowości. Utwórz tabelę tymczasową, wstaw do niej, a następnie skopiuj do tabeli docelowej. – TomTom
Nie używam wielowątkowości. Zawsze wkładam do pustego stołu. – billybob
Dlaczego w ogóle sqlbulkcopy? Poważnie. Tabele na tej samej bazie danych - po prostu powiedz serwerowi, aby skopiował dane, zamiast pobierać je do programu, aby je przesłać. Wybierz prawo do tabeli docelowej za pomocą jednej instrukcji. – TomTom