How to solve the narrowing proxy warning when using SINGLE_TABLE Inheritance strategy in hibernate?

We have structure something like bellow:

@MappedSuperclass
public abstract class BaseEntity implements Serializable {

    private static final long serialVersionUID = 1L;

    @Id
    private Long id;

    @Override
    public boolean equals(Object o) {
        if (this == o) return true;
        BaseEntity that = (BaseEntity) o;
        if (getId() != null ? !getId().equals(that.getId()) : that.getId() != null) {
            return false;
        }
        return true;
    }

    @Override
    public int hashCode() {
        return Objects.hash(getId());
    }
}

@Entity
@Inheritance(strategy = InheritanceType.SINGLE_TABLE)
@Table(name = "BASE_ORGANIZATION")
@DiscriminatorColumn(name = "disc")
@DiscriminatorValue("baseOrganization")
public class BaseOrganization extends BaseEntity {

    @Column(name = "TITLE")
    private String title;
}

@Entity
@Inheritance(strategy = InheritanceType.SINGLE_TABLE)
@Table(name = "BASE_PERSONNEL")
@DiscriminatorColumn(name = "disc")
@DiscriminatorValue("basePersonnel")
public class BasePersonnel extends BaseEntity {

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

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

    @ManyToOne(fetch = FetchType.LAZY)
    @JoinColumn(name = "BASE_ORGANIZATION_ID")
    private BaseOrganization baseOrganization;
}

BaseEntity, BasePersonnel and BaseOrganization is in core_project that all projects can used these objects. Now we create a project that depended to core_project. We must to extends BasePeronnel and BaseOrganization based on our business context. For this reason we added some classes in our project like bellow:

@Entity
@DiscriminatorValue("organization")
public class Organization extends BaseOrganization {

    @Column(name = "MISSION_Type")
    private String missionType;
}

@Entity
@DiscriminatorValue("personnel")
public class Personnel extends BasePersonnel {

    @ManyToOne(fetch = FetchType.LAZY)
    @JoinColumn(name = "MISSION_ORGANIZATION_ID")
    private Organization missionOrganization;
}

Our problem is raised, when we wanna to get all personnel. When we called getAllPersonnel method in PersonnelRepository, hibernate logged bellow message:

WARN  o.h.e.i.StatefulPersistenceContext - HHH000179: Narrowing proxy to class org.xyz.organization.Organization - this operation breaks ==

After that, when we see List<Personnel> object, missionOrganization property is null, but baseOrganization property in super class is loaded!

We think when tow class that have SINGLE_TABLE inheritance strategy, hibernate LazyInitializer can not detect correct concrete class.

Also we debugged narrowProxy method in StatefulPersistenceContext class and we understood that concreteProxyClass.isInstance(proxy) returned false. because proxy object have BaseOrganization object in LazyInitializer and concreteProxyClass refer to Organization class!

It’s because of HHH-11280.

There was a Pull Request sent but it got rejected because it was not the best solution to the problem. You might want to study it a little bit and try to provide a fix.

2 Likes