Archief - [PROG][JAVA] Spring: HibernateTemplate en lazy loading

Het archief is een bevroren moment uit een vorige versie van dit forum, met andere regels en andere bazen. Deze posts weerspiegelen op geen enkele manier onze huidige ideeën, waarden of wereldbeelden en zijn op sommige plaatsen gecensureerd wegens ontoelaatbaar. Veel zijn in een andere tijdsgeest gemaakt, al dan niet ironisch - zoals in het ironische subforum Off-Topic - en zouden op dit moment niet meer gepost (mogen) worden. Toch bieden we dit archief nog graag aan als informatiedatabank en naslagwerk. Lees er hier meer over of start een gesprek met anderen.

forloRn_

Legacy Member
Goedenavond,

Stel dat ik twee tabellen heb, Events en Providers. Events bevat naast wat andere kolommen een FK naar providerId. Vanuit het standpunt van Events gezien hebben we dan een many-to-one-relatie. Providers bevat naast zijn PK providerId, nog een displayName.

Ik gebruik in mijn DAO een Spring HibernateTemplate, bijvoorbeeld
Code:
public EventDto getEvent(String eventId) {
    return (EventDto)hibernateTemplate.get(EventDto.class, eventId);
}

In mijn business logic:
Code:
...
EventDto event = eventDao.getEvent(eventId);
event.getProvider().getDisplayName();
...

Ik meen ergens gelezen te hebben dat je bij lazy loading van HibernateTemplate.get() eigenlijk een proxy terugkrijgt, die via de bestaande Session luie properties alsnog kan ophalen uit de database, als je erom vraagt.
Bij het uitvoeren van de laatste regel krijg ik echter een LazyInitializationException, omdat de HibernateTemplate de Session netjes gesloten heeft op het einde van getEvent().

Ligt het aan mij, of is een HibernateTemplate in dat opzicht redelijk waardeloos? De brave jongen op http://www.codechimp.net/?p=24 raadt aan transactions te gebruiken maar dat vind ik geen goede oplossing, omdat 1) ik niets met transactions te maken wil hebben buiten mijn DAO en 2) ik transactions voor eenvoudige leesoperaties redelijk belachelijk vind.

Iemand een oplossing? OpenSessionInViewFilter en OpenSessionInViewInterceptor zijn volgens mij ook geen oplossing aangezien het niet om een webapplicatie gaat - de Hibernate Sessions zijn niet duidelijk afgebakend.

Dank bij voorbaat.

Bavo aka Joske

Legacy Member
Wel, dat is een vrij complexe vraag. Uiteindelijk draait het hem allemaal rond transaction management, en daar ontbeert het je nu aan, omdat je erop rekent dat Spring's HibernateTemplate dat allemaal voor u doet. Dat doet het, maar op zo een beperkt niveau dat je door lazy-loading meteen buiten transactie-zones komt, en in problemen.

De simpelste oplossing is geen lazy objecten te laden met de template, allesmoet binnen zijn of niets. Nu is dat in de meeste enterprise applicaties geen optie, daarom de grote Spring oplossing: Transaction management met Spring

Dit voorbeeld lijkt vrij cmplex maar is goed stap er stap uitgelegd, en is de de facto manier hoe enterprise apps met Spring/Hibernate werken. Je demarceert transacties op uw spring beans (service layer), die worden gebruikt indien aanwezig in je DAO's. Zo kun je je transacties beter scopen, en indien alle lazyoload request binnen die scope vallen zijn er dus geen problemen.

Buiten DI is dit een van de betere redenen om Spring te gebruiken, ik zou zeggen ga ervoor ;)

Dus: Maak transacties rond uw service via Spring AOP (XML niet code) en doe dezelfde calls die je voordien al deed. Het zou moeten werken.

Bavo aka Joske

Legacy Member
Nog juist een andere manier gevonden dat sneller kan helpen, maar niet zo goed schaalt:

http://www.jroller.com/kbaum/entry/orm_lazy_initialization_with_dao (stuk Being lazy in Business Objects)

Dit gebruikt een HibernateInterceptor van Spring om automatisch Hibernate sessies te openen wanneer er wordt gelazyload. Iets simpeler configuratie dan Spring transacties, maar opent er wel veel meer dan nodig (veel kleine ipv 1 grote).
Het archief is een bevroren moment uit een vorige versie van dit forum, met andere regels en andere bazen. Deze posts weerspiegelen op geen enkele manier onze huidige ideeën, waarden of wereldbeelden en zijn op sommige plaatsen gecensureerd wegens ontoelaatbaar. Veel zijn in een andere tijdsgeest gemaakt, al dan niet ironisch - zoals in het ironische subforum Off-Topic - en zouden op dit moment niet meer gepost (mogen) worden. Toch bieden we dit archief nog graag aan als informatiedatabank en naslagwerk. Lees er hier meer over of start een gesprek met anderen.
Terug
Bovenaan