Dzieje się tak, ponieważ DataAdapter używa Optimistic Concurrency domyślnie. Oznacza to, że jeśli próbujesz zaktualizować wiersz, który już nie istnieje w bazie danych lub został zmieniony, aktualizacja z DataAdapter zawiedzie z powyższym wyjątkiem.
Możliwe scenariusze :
- Pomiędzy wybraniem danych do klienta i wysłaniem aktualizacji inny użytkownik usuwa lub aktualizuje ten wiersz ze swojej aplikacji.
- Może być tak, że usuwasz dane z innego miejsca w swojej aplikacji.
Na przykład :
- Wypełniasz
DataTablektóre zostaną użyte do aktualizacji. - Usuwa wiersz z
Code = 1101(na przykład) bezpośrednio z bazy danych, tzn. nie używaszDataTabletutaj. Jest to emulacja innego użytkownika usuwającego wiersz za pomocąCode = 1101z innej aplikacji. Lub jakaś inna część kodu usuwająca wiersz zCode = 1101. - Wybiera wiersz z
Code = 1101zDataTable, ma to na celu pokazanie, że nadal tam jest, mimo że usunąłeś go z samej bazy danych. - Edytuje
Quantitykolumna w wierszu zCode = 1101wDataTable. Należy to zrobić, w przeciwnym razie wywołanie Update zignoruje ten wiersz podczas aktualizacji. - Wykonuje aktualizację, spowoduje to zgłoszenie wyjątku, ponieważ próbujesz zaktualizować wiersz, który (już) nie istnieje w bazie danych.
Jeśli chcesz zaimplementować Last Writer Wins , Dodaj następujący kod:
cb.ConflictOption = ConflictOption.OverwriteChanges;
Jest jeszcze jedna możliwa rzecz:jeśli masz Decimal /numeric jako kolumny w DB mogą powodować ten błąd, nawet jeśli dane wyglądają tak samo. Wynika to z błędu zaokrąglania dziesiętnego.
Ważna uwaga :Zawsze należy używać parameterized queries Przy okazji. Tego rodzaju konkatenacje ciągów są otwarte dla SQL Injection .