Tech I Enjoy Logo

Custom Search




  Home >> Hibernate

Object hierarchy mapping to Database :

Three mapping strategies for handling object heirarchy to database table,
as follows:

1. Table per concrete class
2. Table per class hierarchy
3. Table per subclass

1. Table per concrete class : In this style of mapping, suppose there will be a abstract class or interface and multiple classes are either extending abstract class or implementing this interface, then those concrete classes can be used to persist by mapping to appropriate Table in database. Now I shall try to demonstrate this perticular scenario by using an abstract class as 'A': A.java
package com.techienjoy.hibernate.example;

public abstract class A {
  String str;
  public abstract void setStr(String arg);
  public abstract String getStr();
}
The above abstract class is extended and following concrete class file is made: AImpl.java
package com.techienjoy.hibernate.example;

public class AImpl extends A {

	String subStr;
	long id;
	public String getSubStr() {
		return subStr;
	}
	public void setSubStr(String subStr) {
		this.subStr = subStr;
	}
	public long getId() {
		return id;
	}
	public void setId(long id) {
		this.id = id;
	}
	@Override
	public void setStr(String arg) {
		str = subStr+"***"+arg;
	}
	@Override
    public String getStr() {
    	return str;
    }
    
}
Corresponding HBM mapping is something like as follows:
<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC
   "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
   "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
<hibernate-mapping package="com.techienjoy.hibernate.example">
  <!-- If require, these setting needs to be changed accordingly. -->

  <class name="AImpl" table="AIMPL">
    <id name="id" type="long"/>
    <property name="str" column="STR"/>
    <property name="subStr" column="SUBSTR"/>
  </class>
  <class name="BImpl" table="BIMPL">
    <id name="id" type="long"/> 
    <property name="str" column="STR"/>
    <property name="subStr" column="SUBSTR"/>
  </class>
</hibernate-mapping>
Following code is the Test harness for seeing this example works: Test.java
package com.techienjoy.hibernate.example;

/**
 * This code is provided on "AS IS" basis, without warranty
 * or guaranty of any kind.
 * Author : Ishtek
 * Date: 28-November-2010
 */
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.Transaction;
import org.hibernate.cfg.Configuration;

public class Test {

    private static SessionFactory sessionFactory;

    /**
     * @param args
     */
    public static void main(String[] args) {

        try {
            sessionFactory = new Configuration().configure()
                    .buildSessionFactory();

            A a = new AImpl();

            ((AImpl) a).setSubStr("ASUB1");
            a.setStr("A1");

            Session session = sessionFactory.openSession();
            Transaction tx = session.beginTransaction();
            tx.begin();
            session.saveOrUpdate(a);
            session.flush();
            tx.commit();
            session.close();
        } catch (Exception ex) {
            ex.printStackTrace();
        }

    }

}
As one might have noticed in the code above that I am trying to persist a variable of a abstract class with an instance of a concrete class AImpl. For this example I have used HSQLDB as database server with the hibernate.cfg.xml file configuration as follows:
<?xml version="1.0"?>
<!DOCTYPE hibernate-configuration PUBLIC
"-//Hibernate/Hibernate Configuration DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
  <!-- If require, these setting needs to be changed accordingly. -->
  <session-factory>
    <property name="connection.driver_class">
        org.hsqldb.jdbcDriver
    </property>
    <property name="connection.url">
        jdbc:hsqldb:hsql://localhost
    </property>
    <property name="connection.username">sa</property>
    <property name="connection.password"></property>

    <property name="connection.pool_size">1</property>

    <property name="dialect">
        org.hibernate.dialect.HSQLDialect
    </property>

    <property name="current_session_context_class">
        thread
    </property>

    <property name="cache.provider_class">
        org.hibernate.cache.NoCacheProvider
    </property>

    <property name="show_sql">true</property>
    <property name="hbm2ddl.auto">create</property>  
    
    <mapping resource="com/techienjoy/hibernate/example/Example.hbm.xml"/>
  </session-factory>
</hibernate-configuration>
As one might have noticed that the above configuration is using a Contextual Hibernate session of type thread with no second level cache provider. All the tables related to this example will be automatically created as the hbm2ddl.auto property is set as 'create'. Second part of this example is to use interface instead of an abstract class 'A', so now I change this A.java from abstract class to an interface as follows: A.java
package com.techienjoy.hibernate.example;

public interface A {

  public abstract void setStr(String arg);
  public abstract String getStr();
}
With this interface implementor class looks someting like as follows: AImpl.java
package com.techienjoy.hibernate.example;

public class AImpl implements A {

	String subStr;
	long id;
	public String getSubStr() {
		return subStr;
	}
	public void setSubStr(String subStr) {
		this.subStr = subStr;
	}
	public long getId() {
		return id;
	}
	public void setId(long id) {
		this.id = id;
	}
	@Override
	public void setStr(String arg) {
		subStr = subStr+"***"+arg;
	}
	@Override
    public String getStr() {
    	return subStr;
    }
    
}
All other files in this example won't require to change, but the data in database table changes, on execution of the Test.java client code. 2. Table per class hierarchy : Extending this article to include an example to show one possible way to do mapping of a class hierarchy turned object graph to a single table with the help of a discriminator with hard coded value in the HBM mapping configuration file. For this example I am defined two class files SuperA as the super class and SubA is the sub class that extends SuperA. SuperA
package com.techienjoy.hibernate.example;

public class SuperA {
    
    public String getStr() {
        return str;
    }
    public void setStr(String str) {
        this.str = str;
    }
    String str;
}
SubA.java
package com.techienjoy.hibernate.example;

public class SubA extends SuperA {
    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = name;
    }
    public int getAge() {
        return age;
    }
    public void setAge(int age) {
        this.age = age;
    }
    String name;
    int age;
}
Example.hbm.xml
<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC
   "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
   "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
<hibernate-mapping package="com.techienjoy.hibernate.example">
   <class name="SuperA" table="SUPERA" discriminator-value="SP">
    <id name="str" type="string" column="id"/>
    <discriminator column="DISC" type="string"/>
    <subclass name="SubA" discriminator-value="SB">
      <property name="name" column="NAME"/>
      <property name="age"  column="AGE" type="int"/>
    </subclass>
  </class>
</hibernate-mapping>
In order to test these code I have following Test Harness code as follows: Test.java
package com.techienjoy.hibernate.example;

/**
 * This code is provided on "AS IS" basis, without warranty
 * or guaranty of any kind.
 * Author : TechIEnjoy
 * Date: 28-November-2010
 */
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.Transaction;
import org.hibernate.cfg.Configuration;

public class Test {

    private static SessionFactory sessionFactory;

    /**
     * @param args
     */
    public static void main(String[] args) {

        try {
            sessionFactory = new Configuration().configure()
                    .buildSessionFactory();
            SuperA a = new SubA();
            a.setStr("test");
            ((SubA) a).setName("Name");
            ((SubA) a).setAge(30);
            Session session = sessionFactory.openSession();
            Transaction tx = session.beginTransaction();
            tx.begin();
            session.saveOrUpdate(a);
            session.flush();
            tx.commit();
            session.close();
        } catch (Exception ex) {
            ex.printStackTrace();
        }

    }

}
Once this program is executed one can find a table created with name as 'SUPERA' with the record as
ID  |DISC | Name | age
test| SB   | Name  |  30
Now extending this example by adding another sub class 'SubB' that extends SuperA class. SubB.java
package com.techienjoy.hibernate.example;

public class SubB extends SuperA {

    String address;
    int postalCode;
    public String getAddress() {
        return address;
    }
    public void setAddress(String address) {
        this.address = address;
    }
    public int getPostalCode() {
        return postalCode;
    }
    public void setPostalCode(int postalCode) {
        this.postalCode = postalCode;
    }
}
Example.hbm.xml
<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC
   "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
   "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
<hibernate-mapping package="com.techienjoy.hibernate.example">
   <class name="SuperA" table="SUPERA" discriminator-value="SP">
    <id name="str" type="string" column="id"/>
    <discriminator column="DISC" type="string"/>
    <subclass name="SubA" discriminator-value="SB">
      <property name="name" column="NAME"/>
      <property name="age"  column="AGE" type="int"/>
    </subclass>
    <subclass name="SubB" discriminator-value="SB1">
      <property name="address" column="AD"/>
      <property name="postalCode"  column="POSTALCODE" type="int"/>
    </subclass>
  </class>
</hibernate-mapping>
Test.java
package com.techienjoy.hibernate.example;

/**
 * This code is provided on "AS IS" basis, without warranty
 * or guaranty of any kind.
 * Author : TechIEnjoy
 * Date: 28-November-2010
 */
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.Transaction;
import org.hibernate.cfg.Configuration;

public class Test {

    private static SessionFactory sessionFactory;

    /**
     * @param args
     */
    public static void main(String[] args) {

        try {
            sessionFactory = new Configuration().configure()
                    .buildSessionFactory();
            SuperA a = new SubA();
            a.setStr("test");
            ((SubA) a).setName("Name");
            ((SubA) a).setAge(30);
            SuperA a1 = new SubB();
            a1.setStr("test1");
            ((SubB) a1).setAddress("Address 1");
            ((SubB) a1).setPostalCode(30056);
            Session session = sessionFactory.openSession();
            Transaction tx = session.beginTransaction();
            tx.begin();
            session.saveOrUpdate(a);
            session.saveOrUpdate(a1);
            session.flush();
            tx.commit();
            session.close();
        } catch (Exception ex) {
            ex.printStackTrace();
        }

    }

}
3. Table per subclass : In this strategy we can have one table for all the class in the class hierarchy and a column in the table that is mapped to the subclass and is not inherited fields from the sub class. Example.hbm.xml
<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC
   "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
   "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
<hibernate-mapping package="com.techienjoy.hibernate.example">
   <class name="SuperA" table="SUPERA">
    <id name="str" type="string" column="id"/>
    
    <joined-subclass name="SubA" table="SUBA">
      <key column="SUBAID" />
      <property name="name" column="NAME"/>
      <property name="age"  column="AGE" type="int"/>
    </joined-subclass>
    <joined-subclass name="SubB" table="SUBB">
      <key column="SUBBID" />
      <property name="address" column="ADDR"/>
      <property name="postalCode"  column="POSTALCODE" type="int"/>
    </joined-subclass>
  </class>
</hibernate-mapping>
I am using all these Java example class files: SuperA.java, SubA.java, SubB.java By using the same Test Harness as follows: Test.java
package com.techienjoy.hibernate.example;

/**
 * This code is provided on "AS IS" basis, without warranty
 * or guaranty of any kind.
 * Author : IQTF
 * Date: 28-November-2010
 */
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.Transaction;
import org.hibernate.cfg.Configuration;

public class Test {

    private static SessionFactory sessionFactory;

    /**
     * @param args
     */
    public static void main(String[] args) {

        try {
            sessionFactory = new Configuration().configure()
                    .buildSessionFactory();
            SuperA a = new SubA();
            a.setStr("test");
            ((SubA) a).setName("Name");
            ((SubA) a).setAge(30);
            SuperA a1 = new SubB();
            a1.setStr("test1");
            ((SubB) a1).setAddress("Address 1");
            ((SubB) a1).setPostalCode(30056);
            Session session = sessionFactory.openSession();
            Transaction tx = session.beginTransaction();
            tx.begin();
            session.saveOrUpdate(a);
            session.saveOrUpdate(a1);
            session.flush();
            tx.commit();
            session.close();
        } catch (Exception ex) {
            ex.printStackTrace();
        }

    }

}
On execution of this Test Harness, one can see records inserted in three tables, 'SUBA', 'SUBB', 'SUPERA' as follows, respectively:
SUBAID |NAME |AGE
test |Name |30
SUBBID |ADDR |POSTALCODE
test1 |Address 1 |30056
ID
test
test1
If anything missed out , please let me know at techienjoy at yahoo . com
Hibernate Bag Mapping Example :
class mapping using Bag Tag example using Hibernate
Framework and a simple to follow steps.
Class Hierarchy Mapping Example :
class hierarchy mapping example using Hibernate
Framework and a simple to follow steps.
Hibernate Example on composite Primary key :
Example on using Hibernate Framework
to work with mapping using composite
Primary key.
List of Examples on Hibernate :
List of example using Hibernate.
Hibernate Interceptor Example :
Example on using Interceptor using Hibernate Framework
with source code explained.
Hibernate Transaction on JBoss :
Explaining Transaction using Hibernate
on JBoss Application Server.
Hibernate Interview Questions :
Interview Questions on Hibernate with answer.
Hibernate class heirarchy mapping :
Hibernate Example on mapping
class hierarchy using various ways
of persisting into database
tables.
Hibernate Join Example :
Using Table join explained with an example
while using Hibernate Framework.
Hibernate one to one mapping Example :
one to one mapping explained using an example
and Hibernate Framework.
Hibernate one to many mapping Example :
one to many mapping explained using an example
and Hibernate Framework.
Hibernate Component Property :
Hibernate Example on Component 
with source code explained.
Example on persisting Class Hierarchy :
Example on using Hibernate Framework
to persist Class Hierarchy into database.
Hibernate Example on Filter :
Example on using Filter using Hibernate Framework
to work with.
Hibernate Named Query Example :
Named Query markup using an example
and Hibernate Framework.
Hibernate one to many mapping Example :
one to many mapping explained using an example
and Hibernate Framework.
Hibernate Property Formula :
Hibernate Example on Property
Tag with ease to do code walk-through
Hibernate Many to Many Mapping Example :
Many to many mapping example using Hibernate
Framework and a simple to follow steps.
Hibernate Insert Update control :
Hibernate Example on controlling
insert and update attributes
Hibernate Example on Filter Criteria :
Example on using Filter Criteria
using Hibernate Framework to work with.


References :
Tags: Hibernate Class Hierarchy Persist example
Tags: Hibernate composite primary key
Tags: Hibernate criteria filter example
Tags: Hibernate Filter Example
Tags: Hibernate Interceptor example
Tags: Hibernate Interview Questions
Tags: Hibernate join example
Tags: Hibernate Many to Many Mapping Example
Tags: Hibernate mapping bag
Tags: Hibernate mapping class hierarchy table per subclass
Tags: Hibernate named query markup
Tags: Hibernate One to Many mapping example
Tags: Hibernate One To One Mapping Example
Tags: Hibernate scenario one to many
Tags: Hibernate transaction jboss
Tags: Hibernate



DISCLAIMER :
The content provided in this page is not warranted and/or guaranteed by techienjoy.com. 
techienjoy.com is not liable for any negative consequences that may result/arise from 
implementing directly/indirectly any information covered in these pages/articles/tutorials.

All contents of this site is/are written and provided on an "AS IS" basis,
without WARRANTIES or conditions of any kind, either express or implied, including, without
limitation, merchantability, or fitness for a particular purpose. You are solely responsible
for determining the appropriateness of using or refering this and assume any risks associated
with this.

In spite of all precautions taken to avoid any typo in these pages, there might be some 
issues like grammatical mistakes and typos being observed in these pages, techienjoy.com
extends sincerest apologies to all our visitors for the same.



Android Examples || Android Examples

© Copyright 2010-2012, TECHIENJOY, All Rights Reserved.      Privacy Policy     Disclaimer & Terms & Conditions