Hello everyone,
I've got a question regarding Hibernate's default fetching strategy in <many-to-one>-Mappings. (I tried to search the forum first, but the search function did not work unfortunately.)
I've mapped a class 'Parent' (see below). It contains a hierarchical structure, i.e. it contains a foreign key on itself for the parent and a set of children of itself. The class is mapped lazy="false" just for testing purposes.
I saved one instance of Parent (parentA) to the DB and in a second step tried to save another instance (parentB) where parentA is the parent of parentB. This works fine.
After that I tried to load parentB to see the SQL output for that statement particularly regarding the fact that I mapped the class as lazy="false" (see below). As is apparent from the log output, Hibernate used an outer join to fetch parentB and its parent, parentA. But I didn't specify fetch="join" in the mapping file. I thought that fetch="select" is the default (according to the reference docs) and I expected to see a second select. Only after explicitly setting the fetching strategy to fetch="select" the second select occurs. Why is that so? Why is the default of fetch="select" not applied? Is it because the class is mapped as lazy="false"? I hope someone can enlighten me on that...
Thank you
Martin
Hibernate version: 3.2.5
Mapping documents:
Code:
<hibernate-mapping>
<class name="Parent" table="parent" lazy="false">
<id name="id" column="id" type="int">
<generator class="native"/>
</id>
<property name="name" column="name" not-null="true"/>
<set name="children" lazy="true">
<key column="parent"/>
<one-to-many class="Parent"/>
</set>
<many-to-one name="parent" column="parent" />
</class>
</hibernate-mapping>
Code between sessionFactory.openSession() and session.close():Code:
// here parentA is created and saved to the DB.
// Session was opened and closed again.
// here parentB is created and saved to the DB (parentA has been set as the parent).
// Session was opened and closed again.
// here I'm trying to load parentB (the ID comes from the save()-statement earlier) and print out its name.
// A new session is used.
parentB = (Parent) session.load(Parent.class, parentBId);
System.out.println(parentB.getName());
...
Name and version of the database you are using: HSQLDB 1.8
The generated SQL (show_sql=true):This is the Hibernate SQL log output for the load()-statement:
Code:
select
parent0_.id as id9_1_,
parent0_.name as name9_1_,
parent0_.parent as parent9_1_,
parent1_.id as id9_0_,
parent1_.name as name9_0_,
parent1_.parent as parent9_0_
from
parent parent0_
left outer join
parent parent1_
on parent0_.parent=parent1_.id
where
parent0_.id=?