Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

how to unproxy a hibernate object [duplicate]

Tags:

java

hibernate

How can I unproxy a hibernate object, such that polymorphism would be supported?

Consider the following example. Classes A and B are two hibernate entities. B has two subtypes C and D.

List<A> resultSet = executeSomeHibernateQuery();
for(A nextA : resultSet) {
    for(B nextB : nextA.getBAssociations() {
        if(nextB instanceof C) {
            // do something for C
        } else if (nextB instanceof D) {
            // do something for D
        }
    }
}

This code fails to execute either the C or D block, since the B collection has been lazy loaded, and all instances of B are Hibernate proxies. I'd like a way to unproxy each instance.

Note: I realize the query can be optimized to eagerly fetch all B's. I'm looking for an alternative.

like image 554
Peter Bratton Avatar asked Jun 27 '12 14:06

Peter Bratton


People also ask

What is Hibernate unproxy?

Hibernate generates the proxy class as a subclass of your entity class. Since version 5.3, Hibernate uses Byte Buddy to generate it at runtime. In older versions, Hibernate used Javassist or CGLIB. The generated proxy intercepts all method invocations, checks if the proxied entity object has been initialized.

Which method returns proxy object in hibernate?

getStreet() , Hibernate will hit the database to fetch the values for the associated entity and initialize it. Hibernate also returns a proxy object when you ask for an entity using the load method instead of the get method of the Session class.

What is JPA proxy?

The JPA lazy loading mechanism can either be implemented using Proxies or Bytecode Enhancement so that calls to lazy associations can be intercepted and relationships initialized prior to returning the result back to the caller.

How to initialize proxy in Hibernate?

Hibernate. initialize(entity. getXXX()) will force the initialization of a proxy entity or collection entity. getXXX() as long as the Session is still open.


2 Answers

Here's our solution, added to our persistence utils:

public T unproxy(T proxied)
{
    T entity = proxied;
    if (entity instanceof HibernateProxy) {
        Hibernate.initialize(entity);
        entity = (T) ((HibernateProxy) entity)
                  .getHibernateLazyInitializer()
                  .getImplementation();
    }
    return entity;
}
like image 74
Peter Bratton Avatar answered Sep 18 '22 18:09

Peter Bratton


Nowadays Hibernate has dedicated method for that: org.hibernate.Hibernate#unproxy(java.lang.Object)

like image 43
Radek Postołowicz Avatar answered Sep 16 '22 18:09

Radek Postołowicz