Search code examples
javaperformancehibernateinheritancehql

Table per subclass inheritance relationship: How to query against the Parent class without loading any subclass ??? (Hibernate)


Suppose a Table per subclass inheritance relationship which can be described bellow (From wikibooks.org - see here)

Notice Parent class is not abstract

@Entity
@Inheritance(strategy=InheritanceType.JOINED)
public class Project {

    @Id
    private long id;

    // Other properties

}

@Entity
@Table(name="LARGEPROJECT")
public class LargeProject extends Project {

    private BigDecimal budget;

}

@Entity
@Table(name="SMALLPROJECT")
public class SmallProject extends Project {

}

I have a scenario where i just need to retrieve the Parent class. Because of performance issues, What should i do to run a HQL query in order to retrieve the Parent class and just the Parent class without loading any subclass ???


Solution

  • A workaround is described below:

    Define your Parent class as MappedSuperClass. Let's suppose the parent class is mapped To PARENT_TABLE

    @MappedSuperClass
    public abstract class AbstractParent implements Serializable {
    
        @Id
        @GeneratedValue
        private long id;
    
        @Column(table="PARENT_TABLE")        
        private String someProperty;
    
        // getter's and setter's
    
    }
    

    For each subclass, extend the AbstractParent class and define its SecondaryTable. Any persistent field defined in the parent class will be mapped to the table defined by SecondaryTable. And finally, use AttributeOverrides if needed

    @Entity
    @SecondaryTable("PARENT_TABLE")
    public class Child extends AbstractParent {
    
        private String childField;
    
        public String getChildProperty() {
            return childField;
        }
    
    }
    

    And define another Entity with the purpose of retrieving just the parent class

    @Entity
    @Table(name="PARENT_TABLE")
    @AttributeOverrides({
        @AttributeOverride(name="someProperty", column=@Column(name="someProperty"))
    })
    public class Parent extends AbstractParent {}
    

    Nothing else. See as shown above i have used just JPA specific annotations