Ho un'applicazione che espone una serie di servizi Web. Una delle mie entità ha un mucchio di relazioni uno-a-molti e molti-a-molti con altre entità. Il mio livello di transnazionalità è in DAO e mi piacerebbe tenerlo lì per evitare che il contesto di persistenza venga aperto troppo a lungo. Pensare di spostarlo fino al livello di servizio o specialmente lasciandolo aperto per la richiesta completa mi dà i timori. Quindi ho dovuto contrassegnare tutte le associazioni come ansiose.
Il risultato è ovviamente che quando lo si recupera, Hibernate genera una query massiccia che sta iniziando a rallentare. Sono andato con 'l'ottimizzazione prematura è la radice di tutti i mali', ma è qualcosa che deve essere già affrontato.
Il mio problema è che, dato che voglio mantenere @Transactional
a livello di DAO, ho due opzioni (abbastanza simili):
-
Impostare le associazioni come pigre e interrogare manualmente DB e impostarle prima di ottenere una proprietà corrispondente. Quindi, dove ho
// entity @OneToMany(fetch = EAGER, mappedBy = "user", cascade = {ALL}, orphanRemoval = true) private final Set<Order> orders = new HashSet<>(); // usage user.getOrders()
Mi piacerebbe cambiare:
// entity
@OneToMany(fetch = LAZY, mappedBy = "user", cascade = {ALL}, orphanRemoval = true)
private final Set<Order> orders = new HashSet<>();
// usage
Set<Order> orders = orderDao.findByUserId(user.getId());
user.setOrders(orders);
user.getOrders()
Questo non mi sembra giusto, perché capisco che lo scopo di avere una relazione Hibernate è lasciare che Hibernate lo gestisca. D'altra parte, avrei comunque il vantaggio di avere Hibernate nella gestione degli aggiornamenti e degli inserti.
- Rimuovi completamente la relazione al livello di Hibernate e gestiscili completamente manualmente. Certo, questo non è estremamente, ma piuttosto doloroso.
C'è qualche altra opzione? Qual è il solito percorso di ottimizzazione in casi come questo?