home.


Tagged: java-hibernate


Java: Hibernate p3: annotations

Instead of using a mapping XML file, we can use Java annotations. First make sure you have the dependencies for annotations and the simple logging facade used by hibernate when using annotations. You need:

  • hibernate-annotations
  • slf4j-api

Previously in the hibernate.cfg.xml file we had a reference to a mappings file. Remove that.

Now set up your hibernate configuration differently in your main java file. Now we now use AnnotationConfiguration, and add two files for annotation. There are different ways to add files for annotation, in XML etc.

    factory = new AnnotationConfiguration()
        .addAnnotatedClass(Employee.class)
        .addAnnotatedClass(Certificate.class)
         .configure()
         .buildSessionFactory();

Finally Annotate the class files. In Employee we say it’s an @Entity, and state the @Table it belongs to. The @Id and @GenerateValue correspond to what we put in the XML file previously. The @Column annotation states its column name in the table.

    ...
    import javax.persistence.*;

    @Entity
    @Table(name="employee")
    public class Employee {
       @Id @GeneratedValue
       @Column(name = "id")
       private long id = 1L;

    @Column(name = "name")
    private String name;


    @OneToMany(cascade=CascadeType.ALL, targetEntity=model.Certificate.class)
    @JoinColumn(name="employee_id")
    private Set certificates;
    ...

The final variable says there’ll be a one-to-many linkage. We state the targetEntity (we wouldn’t need this if we we’re using generics). Then we state the join column name in the Certificates table.

The rest of the file is the same as before. The Certificate file only differs as above:

    ...
    import javax.persistence.*;

    @Entity
    @Table(name="certificate")
    public class Certificate {

       @Id @GeneratedValue
       @Column(name = "id")
       private long id = 1L;

       @Column(name = "cert_name")
       private String name;

Et Voila.

java java-hibernate

Java: Hibernate p2: mappings

To create a mapping, a one to many in this case, we first need to edit the src/main/resources/Employee.hbm.xml file to state the mapping.

    <class name="model.Employee" table="employee">
       <id name="id" column="id" type="long">
         <generator class="native"></generator>
       </id>
       <property name="name" column="name" type="string"></property>
           <set name="certificates" cascade="all">
          <key column="employee_id"/>
          <one-to-many class="model.Certificate"/>
           </set>      
    </class>

    <class name="model.Certificate" table="certificate">
          <id name="id" type="long" column="id">
        <generator class="native"/>
          </id>
          <property name="name" column="cert_name" type="string"/>
     </class>

Note the new set tag. This means we’ll store the new classes in a java Set. We give it a name that will relate to the name in the Certificate class we’ll make. cascade=all means that we’ll persist the Certificates as the same time as Employee. We then set the key column in our to-be-created certificate table, and the fact it’s going to be a one-to-many table using the class as model.Certificate. We finally create a new class tag that is the same as the one we created in the previous tutorial.

The Employee class we defined before only changes in that we create a new Set of the Certificate classes, and make the setters and getters.

    ...
    private Set certificates;
    ...
    public Set getCertificates() {
        return certificates;
    }
    public void setCertificates(Set certificates) {
        this.certificates = certificates;
    } 
    ...   

Now here’s the Certificate class:

    package model;

    public class Certificate {

       private long id = 1L;

       private String name;

       public Certificate() {
       }

       public Certificate(String fname) {
         name = fname;
       }

       public long getId() {
         return id;
       }

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

       public String getName() {
         return name;
       }

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

It’s possible that you may need to implement compareTo() and hashCode() in some instances.

Now in the main class file, First create a Set with the certificates in, then you can add them to the Employee, and then save the employee.

    HashSet set = new HashSet();
    Certificate cert = new Certificate("some python shit");
    Certificate cert1 = new Certificate("some go shit");
    set.add(cert); set.add(cert1);

    ...

    Employee employee = new Employee("name");
    employee.setCertificates(set);
    employeeID = (Long) session.save(employee);       

When you delete an employee, it will also delete its certificates.

java java-hibernate

Java: Hibernate p1: with SQLite

First hibernate needs a small army of jars. You need:

  • hibernatesqlite
  • hibernate-entitymanager
  • sqlite-jdbc

Now create a sqlite3 database in your current directory. Give it an id for the primary key and a text name column. Call them ‘id’ and ‘name’. Name the table employee. Name the file dby.db.

Then in src/main/resources create your hibernate.cfg.xml file. This states you’re going to use a sqlite db, your using it the reference to the db your previously created, and your specifying a mapping that we’ll get to next.

    <?xml version="1.0" encoding="utf-8"?>
    <!DOCTYPE hibernate-configuration SYSTEM 
    "http://www.hibernate.org/dtd/hibernate-configuration-3.0.dtd">

    <hibernate-configuration>
       <session-factory>

       <property name="hibernate.dialect">
          com.applerao.hibernatesqlite.dialect.SQLiteDialect
       </property>
       <property name="hibernate.connection.driver_class">
         org.sqlite.JDBC
       </property>
       <property name="hibernate.connection.url">
       jdbc:sqlite:dby.db
       </property>

       <mapping resource="Employee.hbm.xml"/>

       </session-factory>
    </hibernate-configuration>

In the same directory we’re going to create that mapping between your DB and a java class.

    <?xml version="1.0" encoding="UTF-8"?>
    <!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN" 
    "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
    <hibernate-mapping>
    <class name="model.Employee" table="employee">
       <id name="id" column="id" type="long">
         <generator class="native"></generator>
       </id>
       <property name="name" column="name" type="string"></property>
    </class>
    </hibernate-mapping>

It’s saying we have a class called employee in Employee, which relates to the employee take in the database. It say it has both a id and a name property, which are of the type long and string respectively. The id tag uses the generator native to say make it autoincrement.

Now we need to actually create that class, src/main/java/model/Employee.java. It a Plain Old Java Object.

    package model;

    public class Employee {

       private long id = 1L;

       private String name;

       public Employee() {
       }

       public Employee(String fname) {
         name = fname;
       }

       public long getId() {
         return id;
       }

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

       public String getName() {
         return name;
       }

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

Now we need to create our class that actually deals with that. We first create a SessionFactory. This allows us to make session requests that actually talk to the DB:

    try{
     mFctory = new Configuration().configure().buildSessionFactory();
    }catch (Throwable ex) { 
     System.err.println("Couldn't create session factory." + ex);
     throw new ExceptionInInitializerError(ex); 
    }

Now we have that we can use it to save an Employee we make.

    Session session = mFactory.openSession();
    Transaction tx = null;
    Long employeeID = null;
    try{
     tx = session.beginTransaction();
     Employee employee = new Employee(fname);
     employeeID = (Long) session.save(employee); 
     tx.commit();
    }catch (HibernateException e) {
     if (tx!=null) tx.rollback();
     e.printStackTrace(); 
    }finally {
     session.close(); 
    }

We first get open a session via the factory, then begin a transaction, save your employee to that session, and commit it. The Employee should not be saved to the database.

Getting objects from the database is very much the same:

     List employees = session.createQuery("FROM Employee").list(); 

We’re create a query with HQL that gets everything from ‘Employee’.

Updating a query is a matter of getting the object from the session variable, and then setting that to update:

     Employee employee = (Employee)session.get(Employee.class, itsID); 
     session.update(employee); 

Deleting is the same, except you run session.delete() in place of session.update().

java java-hibernate

Page 1 of 1