1

I would like to inject on all session.save() like below.

public class MyHbnSession implements Session {

       @Override
       public Serializable save(Object obj) throws HibernateException {
           if(obj instanceof MyClass) {
               MyClass mc = (MyClass) obj;
               mc.setVal("Injected Prop");
           }
           return super.save(obj);
       }
}

And then whenever i getSession i should receive my custom session object

MyHbnSession session = HibernateUtil.getSessionFactory().openSession();

I could not find how to do this with hibernate. And two major things i miss

  • org.hibernate.Session is an interface and org.hibernate.impl.SessionImpl is the actual implementation. But in this case the session is implemented
  • How to tell hibernate that this is our custom session implementation and this should be used by the session factory

Kindly throw me some light on what i'm missing. Thanks for any help.

PS : I can do it with aspectj but don't want to due to many reasons.

Vivek
  • 3,523
  • 2
  • 25
  • 41

2 Answers2

2

I personnaly wouldn't override session, but use the JPA annotation @PreUpdate and @PrePersist.

This way you directly modify the needed object, possibly and abstract class containing the "val" if you need it for many classes.

This way you won't have to use the "instanceof " and make the code of the entities more readable.

pdem
  • 3,880
  • 1
  • 24
  • 38
  • Thanks @pdem for the hint, but these JPA annotations didn't work with hibernate. – Vivek Jun 24 '19 at 05:11
  • @Vivek, this not much work to switch from hibernate to JPA, use an entityManager instead of a session. There are Hibernate-JPA annotation to keep Hibernate specific functionnalities. – pdem Jun 24 '19 at 08:15
0

With the help of @pdem answer hint and this post i was able to solve the problem. Here's the gist of what i did.

Interceptor Implementation

import java.io.Serializable;

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

public class MyHbnInterceptor extends EmptyInterceptor {

    /**
     * 
     */
    private static final long serialVersionUID = 1L;

    @Override
    public boolean onSave(Object entity, Serializable id, Object[] state, String[] propertyNames, Type[] types) {
        if(entity instanceof MyClass) {
            // TODO: Do your operations here
        }
        return super.onSave(entity, id, state, propertyNames, types);
    }
}

Letting know hibernate about our interceptor can be done in two ways

  • Session Scope - applies only to the created session
Session session = sf.openSession( new MyHbnInterceptor() );
  • Session Factory Scope - applies to all the session created by the session factory
new Configuration().setInterceptor( new MyHbnInterceptor() );

Know more in this link.

Cheers!

Vivek
  • 3,523
  • 2
  • 25
  • 41