1
Sponsored Links


Ad by Google
In our previous post we have seen the example of Data Filter and in this post we are going to show you the implementation of one of the very powerful feature of Hibernate called Interceptor.

The Interceptor in Hibernate provides callback from the session to the application, allowing the application to inspect and/or manipulate the properties of a persistent object just before it is saved,update,delete,load from the database. One of the common use of interceptor is to track the activity of the application.

For example, In this tutorial we are going to track the activity of the operation performed on the user object, like if any new user is added/updated/delete into the user table, at the same time it will also create a new record inside the user_activity_tracker table.

Two ways to implement interceptor in Hibernate, by extending EmptyInterceptor or by implementing Interceptor interface. In this tutorial we are using EmptyInterceptor class with few common methods of Interceptor interface.

Below are the methods we are using in this example-
  • public void onDelete(Object entity, Serializable id, Object[] state, String[] propertyNames, Type[] types)
  • public boolean onFlushDirty(Object entity, Serializable id, Object[] currentState, Object[] previousState, String[] propertyNames, Type[] types)
  • public boolean onLoad(Object entity, Serializable id, Object[] state, String[] propertyNames, Type[] types)
  • public boolean onSave(Object entity, Serializable id, Object[] state, String[] propertyNames, Type[] types)
  • public void preFlush(Iterator iterator)
  • public void postFlush(Iterator iterator)

Below are the ER diagram of the tables we are using for this project.


Tools and Technologies we are using here:

  • JDK 7
  • Hibernate 4.3.7
  • MySql 5.1.10
  • Eclipse Juno 4.2
  • Maven 3.2

Main Objects of this project are:
  • pom.xml
  • hibernate.cfg.xml
  • annotated pojo
  • database

Overview of the Project Structure:

Create Database Script:

CREATE DATABASE `hibernate_tutorial` ;

USE `hibernate_tutorial`;

/*Table structure for table `user` */

DROP TABLE IF EXISTS `user`;

CREATE TABLE `user` (
  `user_id` bigint(20) NOT NULL AUTO_INCREMENT,
  `email_id` varchar(255) DEFAULT NULL,
  `first_name` varchar(255) DEFAULT NULL,
  `user_name` varchar(255) DEFAULT NULL,
  PRIMARY KEY (`user_id`)
) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=latin1;

/*Table structure for table `user_activity_tracker` */

DROP TABLE IF EXISTS `user_activity_tracker`;

CREATE TABLE `user_activity_tracker` (
  `activity_id` bigint(20) NOT NULL AUTO_INCREMENT,
  `activity` varchar(255) DEFAULT NULL,
  `created_at` datetime DEFAULT NULL,
  PRIMARY KEY (`activity_id`)
) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=latin1;

Create hibernate.cfg.xml

<?xml version='1.0' encoding='utf-8'?>
<!DOCTYPE hibernate-configuration PUBLIC
        "-//Hibernate/Hibernate Configuration DTD 3.0//EN"
        "http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">
  
<hibernate-configuration>
    <session-factory>
        <property name="connection.driver_class">com.mysql.jdbc.Driver</property>
        <property name="connection.url">jdbc:mysql://localhost:3306/hibernate_tutorial</property>
        <property name="connection.username">root</property>
        <property name="connection.password">root</property>
         
        <property name="dialect">org.hibernate.dialect.MySQL5InnoDBDialect</property>
 
        <!-- Echo all executed SQL to stdout -->
        <property name="show_sql">true</property>
        <property name="format_sql">true</property>
        <property name="hbm2ddl.auto">update</property>
        <mapping class="com.javamakeuse.poc.pojo.User"/>
        <mapping class="com.javamakeuse.poc.pojo.UserActivityTracker"/>
          
    </session-factory>
</hibernate-configuration>

Create User.java

package com.javamakeuse.poc.pojo;

import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.Table;

@Entity
@Table(name = "user")
public class User {
 @Id
 @GeneratedValue(strategy = GenerationType.IDENTITY)
 @Column(name = "user_id")
 private long userId;

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

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

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

 public long getUserId() {
  return userId;
 }

 public void setUserId(long userId) {
  this.userId = userId;
 }

 public String getUserName() {
  return userName;
 }

 public void setUserName(String userName) {
  this.userName = userName;
 }

 public String getFirstName() {
  return firstName;
 }

 public void setFirstName(String firstName) {
  this.firstName = firstName;
 }

 public String getEmailId() {
  return emailId;
 }

 public void setEmailId(String emailId) {
  this.emailId = emailId;
 }

}

Create UserActivityTracker.java

package com.javamakeuse.poc.pojo;

import java.util.Date;

import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.Table;

@Entity
@Table(name = "user_activity_tracker")
public class UserActivityTracker {

 @Id
 @GeneratedValue(strategy = GenerationType.IDENTITY)
 @Column(name = "activity_id")
 private long activityId;

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

 @Column(name = "created_at")
 private Date createdAt;

 public UserActivityTracker(String activity, Date createdAt) {
  super();
  this.activity = activity;
  this.createdAt = createdAt;
 }

}

Create HibernateUtility.java Here we are configuring interceptor.

package com.javamakeuse.poc.util;

import org.hibernate.SessionFactory;
import org.hibernate.boot.registry.StandardServiceRegistryBuilder;
import org.hibernate.cfg.Configuration;
import org.hibernate.service.ServiceRegistry;

public class HibernateUtility {
 private static final SessionFactory sessionFactory = buildSessionFactory();

 private static SessionFactory buildSessionFactory() {
  Configuration configuration = new Configuration()
    .setInterceptor(new ActivityTrackerInterceptor());
  configuration.configure();

  ServiceRegistry serviceRegistry = new StandardServiceRegistryBuilder()
    .applySettings(configuration.getProperties()).build();
  SessionFactory sessionFactory = configuration
    .buildSessionFactory(serviceRegistry);

  return sessionFactory;
 }

 public static SessionFactory getSessionFactory() {
  return sessionFactory;
 }

}

Create ActivityTrackerInterceptor class by extending EmptyInterceptor

package com.javamakeuse.poc.util;

import java.io.Serializable;
import java.util.Calendar;
import java.util.Iterator;

import org.hibernate.EmptyInterceptor;
import org.hibernate.Session;
import org.hibernate.type.Type;

import com.javamakeuse.poc.pojo.User;
import com.javamakeuse.poc.pojo.UserActivityTracker;

public class ActivityTrackerInterceptor extends EmptyInterceptor {

 private static final long serialVersionUID = 1L;
 private String operation = "INSERT";
 boolean isMainEntity = false;

 // called when record deleted.
 public void onDelete(Object entity, Serializable id, Object[] state,
   String[] propertyNames, Type[] types) {
  operation = "DELETE";
  isMainEntity = true;
  System.out.println("Delete function called");
 }

 // called when record updated
 public boolean onFlushDirty(Object entity, Serializable id,
   Object[] currentState, Object[] previousState,
   String[] propertyNames, Type[] types) {
  if (entity instanceof User) {
   System.out.println("Update function called");
   operation = "UPDATE";
   isMainEntity = true;
   return true;
  }
  isMainEntity = false;
  return false;
 }

 // called on load events
 public boolean onLoad(Object entity, Serializable id, Object[] state,
   String[] propertyNames, Type[] types) {

  // log loading events
  System.out.println("load function called");
  return true;
 }

 public boolean onSave(Object entity, Serializable id, Object[] state,
   String[] propertyNames, Type[] types) {
  if (entity instanceof User) {
   System.out.println("save function called");
   operation = "INSERT";
   isMainEntity = true;
   return true;
  }
  isMainEntity = false;
  return false;
 }

 // called before commit into database
 public void preFlush(Iterator iterator) {
  System.out.println("Before commiting");
 }

 // called after committed into database
 public void postFlush(Iterator iterator) {
  System.out.println("After commiting");
  if (isMainEntity) {
   Session session = HibernateUtility.getSessionFactory()
     .openSession();
   session.getTransaction().begin();
   UserActivityTracker activityTracker = new UserActivityTracker(
     operation, Calendar.getInstance().getTime());
   session.save(activityTracker);
   session.getTransaction().commit();
  }
  isMainEntity = false;
 }

}

Note: Here we have creating new row in UserActivityTracker table in postFlush() method.

Create Main.java

package com.javamakeuse.poc.dao;

import org.hibernate.Session;

import com.javamakeuse.poc.pojo.User;
import com.javamakeuse.poc.util.HibernateUtility;

public class Main {
 public static void main(String[] args) {
  Session session = HibernateUtility.getSessionFactory().openSession();

  session.beginTransaction();
  User user = new User();

  user.setEmailId("info@javamakeuse.com");
  user.setFirstName("javamakeuse");
  long insertedID = (Long) session.save(user);
  session.getTransaction().commit();

  session.beginTransaction();
  // fetching user
  User user2 = (User) session.load(User.class, insertedID);
  user2.setUserName("javamakeuse");
  session.update(user);

  session.getTransaction().commit();

 }
}

Run Main.java, It will create two records inside user_activity_tracker table one for INSERT and for UPDATE operation.

OUTPUT:

Hibernate: 
    insert 
    into
        user
        (email_id, first_name, user_name) 
    values
        (?, ?, ?)
Before commiting
After commiting
Hibernate: 
    insert 
    into
        user_activity_tracker
        (activity, created_at) 
    values
        (?, ?)
Before commiting
After commiting
Before commiting
Update function called
Hibernate: 
    update
        user 
    set
        email_id=?,
        first_name=?,
        user_name=? 
    where
        user_id=?
After commiting
Hibernate: 
    insert 
    into
        user_activity_tracker
        (activity, created_at) 
    values
        (?, ?)
Before commiting
After commiting

Record inserted in user table.

Record inserted in user_activity_tracker table.


Download the complete example from here Source Code



References
Reference 1
Reference 2

Sponsored Links

1 comments: