JPA @ ManyToOne z CascadeType.Wszystkie
Myślę, że źle zrozumiałem znaczenie kaskadowania w kontekście @ManyToOne
relacji.
Sprawa:
public class User {
@OneToMany(fetch = FetchType.EAGER)
protected Set<Address> userAddresses;
}
public class Address {
@ManyToOne(fetch = FetchType.LAZY, cascade = CascadeType.ALL)
protected User addressOwner;
}
Jakie jest znaczenie cascade = CascadeType.ALL
? Na przykład, jeśli usunę określony adres z bazy danych, w jaki sposób fakt, że dodałem cascade = CascadeType.ALL
wpływa na moje dane (chyba User
)?
5 answers
Znaczenie CascadeType.ALL
jest takie, że persistence będzie propagować (kaskadowo) wszystkie EntityManager
operacje (PERSIST, REMOVE, REFRESH, MERGE, DETACH
) do powiązanych podmiotów.
Wydaje się, że w Twoim przypadku jest to zły pomysł, ponieważ usunięcie Address
doprowadziłoby do usunięcia powiązanego User
. Ponieważ użytkownik może mieć wiele adresów, pozostałe adresy staną się sierotami. Jednak odwrotny przypadek (adnotacja User
) ma sens - jeśli adres należy tylko do jednego użytkownika, bezpiecznie jest propagować usunięcie wszystkich adresów należy do użytkownika, jeśli ten użytkownik zostanie usunięty.
BTW: możesz dodać atrybut mappedBy="addressOwner"
do swojego User
, aby zasygnalizować dostawcy persistence, że kolumna join powinna znajdować się w tabeli adresów.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-05-01 18:25:05
Zobacz tutaj dla przykładu z dokumentów OpenJPA. CascadeType.ALL
oznacza, że wykona wszystkie działania.
Cytat:
CascadeType.PERSIST: utrzymując podmiot, utrzymuj również podmioty utrzymywane w tej dziedzinie. Sugerujemy liberalne zastosowanie tej reguły kaskadowej, ponieważ jeśli EntityManager znajdzie pole, które odwołuje się do nowego encji podczas flush, a Pole nie używa CascadeType.PERSIST, to jest błąd.
CascadeType.Usuń: przy usuwaniu encji również Usuń podmioty znajdujące się w tym polu.
CascadeType.Odśwież: odświeżając obiekt, odśwież również obiekty znajdujące się w tym polu.
CascadeType.MERGE: w przypadku stanu podmiotu łączącego, Scal również podmioty znajdujące się w tym polu.
Sebastian
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-10-10 05:46:05
Użycie elementu adnotacji kaskadowej może być użyte do propagacji wpływ operacji na podmioty powiązane. Kaskada funkcjonalność jest najczęściej używana w relacjach rodzic-dziecko.
Jeśli X jest zarządzaną jednostką, operacja Usuń powoduje, że staje się usunięte. Operacja usuń jest kaskadowa dla jednostek, do których odnosi się X, jeśli relacje z X do tych innych encji są adnotowane za pomocą na cascade = Usuń lub cascade=wszystkie wartości elementu adnotacji.
W skrócie, relacje encji zdefiniowane przez CascadeType.All
zapewnią, że wszystkie zdarzenia persist, takie jak persist, refresh, merge I remove, które występują na rodzicu, zostaną przekazane potomkowi. Definiowanie innych opcji CascadeType
zapewnia programiście bardziej szczegółowy poziom kontroli nad sposobem, w jaki Asocjacja encji obsługuje trwałość.
Na przykład gdybym miał książkę obiektową, która zawierała listę stron i Dodaj obiekt strony do tej listy. Jeśli adnotacja @OneToMany
definiująca powiązanie między książką a stroną jest oznaczona jako CascadeType.All
, utrzymywanie książki spowoduje, że strona zostanie również utrzymana w bazie danych.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-10-10 06:36:05
Jak wyjaśniłem w w tym artykule oraz w mojej książce High-Performance Java Persistence, nigdy nie powinieneś używać CascadeType.ALL
Na @ManyToOne
, Ponieważ przejścia stanu jednostki powinny propagować się z jednostek nadrzędnych do potomnych.
Strona @ManyToOne
jest zawsze asocjacją dziecka, ponieważ powinna odwzorowywać podstawowe FK.
Dlatego przenieś CascadeType.ALL
z asocjacji @ManyToOne
do @OneToMany
, która powinna używać atrybutu mappedBy
, ponieważ jest najbardziej efektywnym mapowanie jeden do wielu .
`
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-01-04 12:28:08
W JPA 2.0 Jeśli chcesz usunąć adres, jeśli usunąłeś go z encji użytkownika, możesz dodać orphanRemoval=true
(zamiast CascadeType.REMOVE
) do swojego @OneToMany
.
Więcej wyjaśnień między orphanRemoval=true
a CascadeType.REMOVE
jest tutaj .
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-10-10 05:09:21