|
View:
New views
4 Messages
—
Rating Filter:
Alert me
|
|
|
Lazy loading can operate when persistence context is closed?Doesn't the persistence context have to be open for a lazy loaded collection to be fetched?
I thought if the persistence context was closed and you attempted to get a lazy loaded collection, you'd get a lazy load exception? (is that just with Hibernate?) I ran this bare bones test and my final assertion fails unexpectedly since when I call contract.getSupplierContracts it actual fires the SQL query to get the collection without error even though the persistence context is closed (and I even committed the xact just to make sure the loop was closed) I am making sure to run the static weaver (org.eclipse.persistence.tools.weaving.jpa.StaticWeave) before running my test. Why is the collection being lazy loaded even when the persistence context is closed??? I'm using EclipseLink 1.1.1, JPA 1.0, against Oracle 10g, on Java SE 6 Here's my persistence.xml <?xml version="1.0" encoding="UTF-8"?> <persistence version="1.0" xmlns="http://java.sun.com/xml/ns/persistence" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/persistence http://java.sun.com/xml/ns/persistence/persistence_1_0.xsd"> <persistence-unit name="JPASpike" transaction-type="RESOURCE_LOCAL"> <provider>org.eclipse.persistence.jpa.PersistenceProvider</provider> <class>jpa.Contract</class> <class>jpa.SupplierContract</class> <class>jpa.Supplier</class> <exclude-unlisted-classes>true</exclude-unlisted-classes> <properties> <property name="eclipselink.jdbc.driver" value="oracle.jdbc.OracleDriver"/> <property name="eclipselink.jdbc.read-connections.min" value="1"/> <property name="eclipselink.jdbc.read-connections.max" value="2"/> <property name="eclipselink.jdbc.write-connections.min" value="1"/> <property name="eclipselink.jdbc.write-connections.max" value="2"/> <property name="eclipselink.weaving" value="static"/> <property name="eclipselink.weaving.lazy" value="true"/> <property name="eclipselink.weaving.fetchgroups" value="false"/> <property name="eclipselink.weaving.changetracking" value="false"/> <property name="eclipselink.orm.throw.exceptions" value="true"/> <property name="eclipselink.logging.level" value="FINE"/> <property name="eclipselink.logging.logger" value="DefaultLogger"/> <property name="eclipselink.target-database" value="Oracle"/> </properties> </persistence-unit> </persistence> Here's a fragment of my mapping with lazy load configured: @OneToMany(fetch = FetchType.LAZY) @JoinTable(name = "SUPPLIER_CONTRACT", joinColumns = @JoinColumn(name = "CONTRACTID", referencedColumnName = "CONTRACTID"), inverseJoinColumns = @JoinColumn(name = "SUPPLIERID", referencedColumnName = "SUPPLIERID")) private List<SupplierContract> supplierContracts = new ArrayList<SupplierContract>(); And here's my test: Integer contractId = 101; Contract contract = null; EntityManager em = Persistence.createEntityManagerFactory("JPASpike").createEntityManager(); EntityTransaction tx = em.getTransaction(); try { tx.begin(); System.out.println("### find contract"); contract = em.find(Contract.class, contractId); tx.commit(); assertNotNull("Contract should be found with id: " + contractId, contract); assertEquals("contract id", contractId, contract.getId()); } catch (Exception e) { System.out.println("Persistence failed: " + e); e.printStackTrace(); if (tx != null) tx.rollback(); // TODO this is failing with IllegalStateException no xact is active fail("Persistence failed: " + e); } finally { System.out.println("### finally"); if (em != null) em.close(); } // Now, outside of the persistence context, make sure the collection is not populated System.out.println("### verify collection not populated"); System.out.println("### em is open: " + em.isOpen()); assertTrue("collection should be empty after initial get", contract.getSupplierContracts().isEmpty()); |
|
|
Re: Lazy loading can operate when persistence context is closed?
More info on this: while inspecting the Contract.class file after the static weaver was applied, it looks like it didn't weave in the lazy loading. Here's the class definition from the class file after StaticWeave was run: public class jpa.Contract implements java.lang.Cloneable, org.eclipse.persistence.internal.weaving.PersistenceWeaved, org.eclipse.persistence.internal.descriptors.PersistenceEntity, org.eclipse.persistence.internal.descriptors.PersistenceObject { It did something since it added the PersistenceWeaved interface but it should have also added the PersistenceWeavedLazy interface. Why didn't it add that even though I added the lazy fetch type on the supplierContracts collection and the eclipselink.weaving.lazy property is set to true? (I do have this working on another class so I'm wondering what I'm missing here) |
|
|
Re: Lazy loading can operate when persistence context is closed?That is just with Hibernate. EclipseLink/TopLink has a feature to allow
loading entities as described by Doug: http://forums.oracle.com/forums/thread.jspa?messageID=1706796 So you can still access lazy loaded attributes as long as the entity has not been serialized. Best Regards, Chris fcalfo wrote: > Doesn't the persistence context have to be open for a lazy loaded collection > to be fetched? > > I thought if the persistence context was closed and you attempted to get a > lazy loaded collection, you'd get a lazy load exception? (is that just with > Hibernate?) > > I ran this bare bones test and my final assertion fails unexpectedly since > when I call > contract.getSupplierContracts it actual fires the SQL query to get the > collection without error even though the persistence context is closed (and > I even committed the xact just to make sure the loop was closed) > > I am making sure to run the static weaver > (org.eclipse.persistence.tools.weaving.jpa.StaticWeave) before running my > test. > > Why is the collection being lazy loaded even when the persistence context is > closed??? > > I'm using EclipseLink 1.1.1, JPA 1.0, against Oracle 10g, on Java SE 6 > > Here's my persistence.xml > > <?xml version="1.0" encoding="UTF-8"?> > <persistence version="1.0" xmlns="http://java.sun.com/xml/ns/persistence" > xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" > xsi:schemaLocation="http://java.sun.com/xml/ns/persistence > http://java.sun.com/xml/ns/persistence/persistence_1_0.xsd"> > <persistence-unit name="JPASpike" transaction-type="RESOURCE_LOCAL"> > <provider>org.eclipse.persistence.jpa.PersistenceProvider</provider> > <class>jpa.Contract</class> > <class>jpa.SupplierContract</class> > <class>jpa.Supplier</class> > <exclude-unlisted-classes>true</exclude-unlisted-classes> > <properties> > <property name="eclipselink.jdbc.driver" > value="oracle.jdbc.OracleDriver"/> > <property name="eclipselink.jdbc.read-connections.min" value="1"/> > <property name="eclipselink.jdbc.read-connections.max" value="2"/> > <property name="eclipselink.jdbc.write-connections.min" value="1"/> > <property name="eclipselink.jdbc.write-connections.max" value="2"/> > <property name="eclipselink.weaving" value="static"/> > <property name="eclipselink.weaving.lazy" value="true"/> > <property name="eclipselink.weaving.fetchgroups" value="false"/> > <property name="eclipselink.weaving.changetracking" value="false"/> > <property name="eclipselink.orm.throw.exceptions" value="true"/> > <property name="eclipselink.logging.level" value="FINE"/> > <property name="eclipselink.logging.logger" value="DefaultLogger"/> > <property name="eclipselink.target-database" value="Oracle"/> > </properties> > </persistence-unit> > </persistence> > > Here's a fragment of my mapping with lazy load configured: > > @OneToMany(fetch = FetchType.LAZY) > @JoinTable(name = "SUPPLIER_CONTRACT", joinColumns = @JoinColumn(name = > "CONTRACTID", referencedColumnName = "CONTRACTID"), inverseJoinColumns = > @JoinColumn(name = "SUPPLIERID", referencedColumnName = "SUPPLIERID")) > private List<SupplierContract> supplierContracts = new > ArrayList<SupplierContract>(); > > And here's my test: > > Integer contractId = 101; > Contract contract = null; > EntityManager em = > Persistence.createEntityManagerFactory("JPASpike").createEntityManager(); > EntityTransaction tx = em.getTransaction(); > > try > { > tx.begin(); > System.out.println("### find contract"); > contract = em.find(Contract.class, contractId); > tx.commit(); > assertNotNull("Contract should be found with id: " + contractId, > contract); > assertEquals("contract id", contractId, contract.getId()); > } > catch (Exception e) > { > System.out.println("Persistence failed: " + e); > e.printStackTrace(); > if (tx != null) > tx.rollback(); // TODO this is failing with > IllegalStateException no xact is active > fail("Persistence failed: " + e); > } > finally > { > System.out.println("### finally"); > if (em != null) > em.close(); > } > > // Now, outside of the persistence context, make sure the collection > is not populated > System.out.println("### verify collection not populated"); > System.out.println("### em is open: " + em.isOpen()); > assertTrue("collection should be empty after initial get", > contract.getSupplierContracts().isEmpty()); > > eclipselink-users mailing list eclipselink-users@... https://dev.eclipse.org/mailman/listinfo/eclipselink-users |
|
|
Re: Lazy loading can operate when persistence context is closed?Hi,
The JPA specification does not specify what the persistence provider should do to lazy relationships when the persistence context is closed. EclipseLink has chosen to retrieve them when possible. Our implementation of lazy relationships for xToMany relationships does not require the use of weaving. We, instead, use a subclass of your collection class. (In your case we use a class called IndirectList - if you want, you can take a look at it in the source to see what it does.) -Tom fcalfo wrote: > > > fcalfo wrote: >> Doesn't the persistence context have to be open for a lazy loaded >> collection to be fetched? >> >> I am making sure to run the static weaver >> (org.eclipse.persistence.tools.weaving.jpa.StaticWeave) before running my >> test. >> >> > > > More info on this: while inspecting the Contract.class file after the static > weaver was applied, it looks like > it didn't weave in the lazy loading. > > Here's the class definition from the class file after StaticWeave was run: > > public class jpa.Contract implements java.lang.Cloneable, > org.eclipse.persistence.internal.weaving.PersistenceWeaved, > org.eclipse.persistence.internal.descriptors.PersistenceEntity, > org.eclipse.persistence.internal.descriptors.PersistenceObject { > > It did something since it added the PersistenceWeaved interface > > but it should have also added the PersistenceWeavedLazy interface. > > Why didn't it add that even though I added the lazy fetch type on the > supplierContracts collection and the eclipselink.weaving.lazy property is > set to true? > > (I do have this working on another class so I'm wondering what I'm missing > here) eclipselink-users mailing list eclipselink-users@... https://dev.eclipse.org/mailman/listinfo/eclipselink-users |
| Free embeddable forum powered by Nabble | Forum Help |