-->
These old forums are deprecated now and set to read-only. We are waiting for you on our new forums!
More modern, Discourse-based and with GitHub/Google/Twitter authentication built-in.

All times are UTC - 5 hours [ DST ]



Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 1 post ] 
Author Message
 Post subject: Double property-proxy fetching bug
PostPosted: Wed May 25, 2005 6:52 am 
Newbie

Joined: Wed Jan 26, 2005 11:01 am
Posts: 18
[b]Description[/b]

When (a) a persisted class has two associated properties of the same type, (b) that type has a proxy, (c) that type has a complex property, only the first association (alphabetically) is eagerly fetchable. If both have an outer-join="true" setting in the mapping, the second is ignored, leading to lazy initialization exceptions.
This is due to how the sql string for the persisted class is constructed (in AbstractEntityLoader.initStatementString). The list of associations that is a parameter there, is constructed by walking the association tree. When walking the association tree, a set of visisted persisters is maintained. The persister for the properties is added to this set when evaluating the complex property of this property. When the visitor wants to visit the second property, the persister is already in the set and the property is not visisted and thus not added to the list of associations and eventually not added to the select statement.
This also leads to unnecessary SELECT statements when loading an object in the described situation where the property is not proxied.
Is this a bug?

[b]Hibernate version:[/b] 2.1.8

[b]Mapping documents:[/b]

<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping SYSTEM "http://hibernate.sourceforge.net/hibernate-mapping-2.0.dtd" >
<hibernate-mapping>
<class name="org.hibernate.test.fetchProxy.Main">
<id name="id" unsaved-value="null">
<generator class="increment"/>
</id>
<many-to-one name="one" outer-join="true" cascade="all"/>
<many-to-one name="two" outer-join="true" cascade="all"/>
</class>
<class name="org.hibernate.test.fetchProxy.Proxied" lazy="true">
<id name="id" unsaved-value="null">
<generator class="increment"/>
</id>
<property name="name"/>
<many-to-one name="spec" cascade="all"/>
</class>
<class name="org.hibernate.test.fetchProxy.Spec">
<id name="id" unsaved-value="null">
<generator class="increment"/>
</id>
</class>
</hibernate-mapping>

[b]Code between sessionFactory.openSession() and session.close():[/b]

Session s;
Main main = new Main();
main.setOne(new Proxied("first"));
main.setTwo(new Proxied("second"));
s = openSession();
Serializable id = s.save(main);
s.flush();
s.close();

s = openSession();
Main persisted = (Main) s.get(Main.class,id);
s.close();

assertEquals("first",persisted.getOne().getName());
assertEquals("second",persisted.getTwo().getName());


public class Main {

private Long id;

private Proxied one;

private Proxied two;

public Long getId() {
return id;
}

public void setId(Long id) {
this.id = id;
}

public Proxied getOne() {
return one;
}

public void setOne(Proxied one) {
this.one = one;
}

public Proxied getTwo() {
return two;
}

public void setTwo(Proxied two) {
this.two = two;
}
}

public class Proxied {

private Long id;

private String name;

private Spec spec;

protected Proxied() {}

public Proxied(String name) {
this.name = name;
}

public Long getId() {
return id;
}

public void setId(Long id) {
this.id = id;
}

public Spec getSpec() {
return spec;
}

public void setSpec(Spec spec) {
this.spec = spec;
}

public String getName() {
return name;
}

public void setName(String name) {
this.name = name;
}
}

public class Spec {

private Long id;

public Long getId() {
return id;
}

public void setId(Long id) {
this.id = id;
}
}

[b]Full stack trace of any exception that occurs:[/b]

net.sf.hibernate.HibernateException: Could not initialize proxy - the owning Session was closed
at net.sf.hibernate.proxy.LazyInitializer.initialize(LazyInitializer.java:47)
at net.sf.hibernate.proxy.LazyInitializer.initializeWrapExceptions(LazyInitializer.java:60)
at net.sf.hibernate.proxy.LazyInitializer.getImplementation(LazyInitializer.java:164)
at net.sf.hibernate.proxy.CGLIBLazyInitializer.intercept(CGLIBLazyInitializer.java:108)
at org.hibernate.test.fetchProxy.Proxied$$EnhancerByCGLIB$$86691509.getName(<generated>)
at org.hibernate.test.fetchProxy.EagerTest.testBothSet(EagerTest.java:47)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
at java.lang.reflect.Method.invoke(Unknown Source)
at junit.framework.TestCase.runTest(TestCase.java:154)
at org.hibernate.test.TestCase.runTest(TestCase.java:107)
at junit.framework.TestCase.runBare(TestCase.java:127)
at junit.framework.TestResult$1.protect(TestResult.java:106)
at junit.framework.TestResult.runProtected(TestResult.java:124)
at junit.framework.TestResult.run(TestResult.java:109)
at junit.framework.TestCase.run(TestCase.java:118)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:421)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:305)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:186)

[b]Name and version of the database you are using:[/b] hypersonic 1.7.3.3


Top
 Profile  
 
Display posts from previous:  Sort by  
Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 1 post ] 

All times are UTC - 5 hours [ DST ]


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum

Search for:
© Copyright 2014, Red Hat Inc. All rights reserved. JBoss and Hibernate are registered trademarks and servicemarks of Red Hat, Inc.