2012-11-05 22 views
11

Używam hibernacji do wstawienia do tabeli mysql, dla której wszystkie kolumny są zdefiniowane jako nie puste. Ma unikalny klucz podstawowy i inny unikalny indeks w kilku kolumnach.org.springframework.dao.DataIntegrityViolationException błędnie zgłaszająca przyczyna?

Dostaję następujący błąd:

org.springframework.dao.DataIntegrityViolationException: Could not execute JDBC batch update; SQL [insert into MY_TABLE(col1, col2, col3, col4, ID_) values (?, ?, ?, ?, ?)]; constraint [null]

Ten błąd jest w dziennikach klienta i nie mogę odtworzyć problemu sam, więc nie mogę umieścić w debugowania, aby zobaczyć, jakie wartości są w instrukcja wstawiania.

Rozumiem, że "ograniczenie [null]" oznacza naruszenie "nie puste". Jednak patrząc na mój kod, nie widzę żadnego możliwego sposobu, aby którykolwiek z danych mógł mieć wartość zerową w momencie wstawienia, chyba że hibernacja próbuje wstawić identyfikator null (co byłoby bardzo złym błędem w hibernacji i tak się wydaje mało prawdopodobne).

Widzę jednak, jak to się dzieje, że naruszane są wyjątkowe ograniczenia. Czy to możliwe, że wiadomość wprowadza w błąd i rzeczywiście otrzymuję wyjątkowe naruszenie klucza? Czy "constraint [null]" zawsze oznacza naruszenie nie zerowe?

+0

nie mogę odgadnąć, dlaczego ten wyjątek jest spowodowany chyba 'nie null' kolumna próbuje dać' wartość null'. BTW, jeśli używasz starszej wersji sterownika JDBC, nie zapomnij go zastąpić najnowszym (10+). W przeciwnym razie spowoduje to również inne problemy również później. – Lion

+0

To jest mysql 5.1, a nie Oracle. – Dana

Odpowiedz

11

Jeśli szukać rozmówców z konstruktora DataIntegrityViolationException w kodzie źródłowym Wiosna, przekonasz się, że to się nazywa w org.springframework.orm.hibernate3.SessionFactoryUtils:

return new DataIntegrityViolationException(ex.getMessage() + "; SQL [" + jdbcEx.getSQL() + 
       "]; constraint [" + jdbcEx.getConstraintName() + "]", ex); 

więc wyjątek spowodowany jest naruszone ograniczenia i null to nazwa ograniczenia zwróconego przez wyjątek JDBC. Powinieneś więc obwiniać sterownik MySQL za niepopełnianie nazwy naruszonego ograniczenia w wyjątku JDBC. Ale naruszone ograniczenie może być dowolnym ograniczeniem, a niekoniecznie ograniczeniem.

+1

Rozumiem, to bardzo denerwujące, że mysql nie podaje nazwy, ale bardzo pomocne jest wiedzieć! Po prostu założyłem, że wartość pusta oznacza nie zerowe ograniczenie. Dzięki. – Dana

1

Możesz uzyskać nazwę Constain bezpośrednio z typu wyjątku Hibernate. Użyj

getConstraintName

Właściwość, aby uzyskać nazwę ograniczenia DB.

} catch (ConstraintViolationException conEx) { 
      if (conEx.getConstraintName().contains("PROJECT_UK")) { 
       //TODO Project Entity is violating it's constrain 

Użyłem zawiera, ponieważ chcę, aby ta aplikacja działała na wielu schematach DB. Domyślnie getConstraintName pochodzi z nazwą DB jak

MyDBName.ConstrainName

+0

Nie ma więcej metody getConstraintName() w wyjątku ConstraintViolationException – Anna

Powiązane problemy