I have a Menu class that has a many-to-may relationship with the
class SingleItem.
When I persist the Menu class along with the collection of SingleItem
objects everything works fine , and also I can retrieve the collection of
objects when I load the Menu class from the database using hibernate.
But when it comes to one-to-one mapping I am having a problem.
I have a SingleItem class that has an Ingredient class as an attribute.
The relationship is one-to-one.
When I persist the SingleItem class along with an Ingredient object
everything works fine, but when I load the SingleItem class from the
database using hibernate I only get the SingleItem class back and not
the Ingredient class which is a part of the SingleItem class.
// the first line works
SingleItem si = (SingleItem)session.load(SingleItem.class,id);
// the second line here below does not work, I dont get an Ingredient
// object
Ingredient ing = si.getIngredient();
below is my code.
Although not all code is needed I have put it all just in case.
The testing class is at the bottom of the list, that's where the
methods that don't work are.
Have a look at the loadItems() method of class Test at the bottom
of the list!
The mapping xml file is just before the Test class, I think that is where
the problem is!
Please let me know what is the problem, regarding the one-to-one
mapping when loading objects!
Thanks in advance!
class Menu
Code:
package examples;
import java.util.*;
public class Menu {
private String name;
private int id;
private int code;
private Map singleitems;
public Menu(){}
public void setId(int i) {
id = i;
}
public int getId() {
return id;
}
public void setCode(int code){
this.code = code;
}
public int getCode(){
return code;
}
public void setSingleitems(Map singleitems){
this.singleitems = singleitems;
}
public Map getSingleitems(){
return singleitems;
}
public void setName(String name){
this.name = name;
}
public String getName(){
return name;
}
}
class SingleItem
Code:
package examples;
import java.util.*;
import java.io.*;
public class SingleItem {
private Ingredient ingredient;
private int id;
private double price;
private int code;
private int qty = 1;
private String name;
public SingleItem(){}
public void setId(int i) {
id = i;
}
public int getId() {
return id;
}
public void setName(String name){
this.name = name;
}
public String getName(){
return name;
}
public void setCode(int code){
this.code = code;
}
public int getCode(){
return code;
}
public void setPrice(double price){
this.price = price;
}
public double getPrice(){
return price;
}
public void setQty(int qty){
this.qty = qty;
}
public int getQty(){
return qty;
}
public void setIngredient(Ingredient ingredient){
this.ingredient = ingredient;
}
public Ingredient getIngredient(){
return ingredient;
}
}
Ingredient
Code:
package examples;
import java.util.*;
public class Ingredient{
private int id;
private String name;
private int code;
private double price;
private int qty = 1;
private double total;
public Ingredient(){}
public Ingredient(String name,int code,double price){
this.name = name;
this.code = code;
this.price = price;
}
public void setId(int i) {
id = i;
}
public int getId() {
return id;
}
public void setName(String name){
this.name = name;
}
public String getName(){
return name;
}
public void setCode(int code){
this.code = code;
}
public int getCode(){
return code;
}
public void setPrice(double price){
this.price = price;
}
public double getPrice(){
return price;
}
public void incrementQty(){
}
public void decrementQty(){
}
public void setQty(int qty){
this.qty = qty;
}
public int getQty(){
return qty;
}
public void setSubTotal(float total){
this.total = total;
}
public double getSubTotal(){
return total;
}
}
hibernate.cfg.xml
Code:
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE hibernate-configuration PUBLIC "-//Hibernate/Hibernate Configuration DTD//EN" "http://hibernate.sourceforge.net/hibernate-configuration-2.0.dtd">
<hibernate-configuration>
<session-factory>
<property name="connection.driver">com.mysql.jdbc.Driver</property>
<property name="connection.url">jdbc:mysql://localhost/examples</property>
<property name="dialect">net.sf.hibernate.dialect.MySQLDialect</property>
<mapping resource="Version.hbm.xml"/>
</session-factory>
</hibernate-configuration>
hibernate properties
Code:
hibernate.dialect net.sf.hibernate.dialect.MySQLDialect
hibernate.connection.driver_class com.mysql.jdbc.Driver
hibernate.connection.url jdbc:mysql://localhost/examples
hibernate.connection.username root
hibernate.connection.password secret
hibernate.show_sql true
hibernate.cglib.use_reflection_optimizer false
session
Code:
import net. sf.hibernate.*;
import net. sf.hibernate.cfg.*;
public class HibernateSession {
private static final SessionFactory sessionFactory;
static {
try {
sessionFactory = new Configuration().configure().buildSessionFactory();
} catch (HibernateException e) {
throw new RuntimeException("SessionFactory Error - " + e.getMessage(), e);
}
}
public static final ThreadLocal session = new ThreadLocal();
public static Session currentSession() throws HibernateException {
Session s = (Session) session.get();
if (s == null) {
s = sessionFactory.openSession();
session.set(s);
}
return s;
}
public static void closeSession() throws HibernateException {
Session s = (Session) session.get();
session. set(null);
if (s != null)
s.close();
}
}
SQL Code
Code:
create table menu (
id int not null auto_increment primary key,
code integer,
name text
);
create table menu_singleitem (
parent_id int,
singleitem_name text,
singleitem_id int);
create table singleitem (
id int not null auto_increment primary key,
price double,
code integer,
qty integer,
name text
);
create table ingredient (
id int not null auto_increment primary key,
price double,
code integer,
qty integer,
name text
);
Version.hbm.xml
Code:
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE hibernate-mapping
PUBLIC "-//Hibernate/Hibernate Mapping DTD//EN"
"http://hibernate.sourceforge.net/hibernate-mapping-2.0.dtd">
<hibernate-mapping>
<class name="examples.Menu"
table="menu">
<id name="id" unsaved-value="0">
<generator class="native"/>
</id>
<map name="singleitems"
table="menu_singleitem" cascade="all">
<key column="parent_id"/>
<index column="singleitem_name" type="string"/>
<many-to-many column="singleitem_id" class="examples.SingleItem"/>
</map>
<property name="name" type="string"/>
<property name="code" type="int"/>
</class>
<class name="examples.SingleItem"
table="singleitem">
<id name="id" unsaved-value="0">
<generator class="native"/>
</id>
<one-to-one
name="ingredient"
class="examples.Ingredient"
cascade="all" />
<property name="name" type="string"/>
<property name="price" type="double"/>
<property name="code" type="int"/>
<property name="qty" type="int"/>
</class>
<class name="examples.Ingredient"
table="ingredient">
<id name="id" unsaved-value="0">
<generator class="native"/>
</id>
<property name="name" type="string"/>
<property name="price" type="double"/>
<property name="code" type="int"/>
<property name="qty" type="int"/>
</class>
</hibernate-mapping>
the testing class
Code:
import examples.*;
import examples.Menu;
import examples.SingleItem;
import examples.Ingredient;
import net.sf.hibernate.*;
import net.sf.hibernate.cfg.*;
import java.util.*;
import java.io.*;
public class Test {
public Test(){}
public void save(){
try {
Session session = HibernateSession.currentSession();
Transaction tx = session.beginTransaction();
Menu menu = new Menu();
menu.setName("Menu to persist");
HashMap map = new HashMap();
SingleItem sl = new SingleItem();
sl.setName("item 1");
Ingredient ing = new Ingredient();
ing.setName("ingredient one");
sl.setIngredient(ing);
HashMap map1 = new HashMap();
map1.put(sl.getName(),sl);
menu.setSingleitems(map1);
session.save(menu);
session.flush();
tx.commit();
session.close();
}
catch (Exception e) {
e.printStackTrace();
}
}
public Menu loadMenu(int id){
Menu menu = new Menu();
try {
Session session = HibernateSession.currentSession();
Transaction tx = session.beginTransaction();
menu = (Menu)session.load(Menu.class,id);
}
catch (Exception e) {
e.printStackTrace();
}
return menu;
}
// this is the method where the problems are
public void loadItems(){
Menu menu = loadMenu(11);
Map map = menu.getSingleitems();
SingleItem si = (SingleItem)map.get("item 1");
System.out.println(si.getName());
// here is the problem
Ingredient ing = si.getIngredient();
System.out.println(ing.getName());
}
}