JPA @Entity Inheritance

13,509

Inheritance in JPA is specified on the root entity using the @Inheritance annotation. There you can specify the database representation of the hierarchy. Check the documentation for more details.

If your child classes define only transient fields (not methods) (i.e. not saved in the db), then perhaps a discriminator column is the best option. But it may be the case that you don't actually need inheritance - the main entity can have all the methods (because it has all the fields the methods operate on)

Share:
13,509
travega
Author by

travega

Updated on June 17, 2022

Comments

  • travega
    travega almost 2 years

    I have been looking into JPA/Hibernate @Entity inheritance for a while now and can't seem to find anything that addresses what I am trying to achieve.

    Basically I want to be able to define an @Entity with all of the column and table mappings as required. Then I want to be able to extend the @Entity in a number of different locations with different sets of @Transient methods defined in the body of each "sub-Entity". This is a basic example of what I am trying to achieve but with no success thus far:

    @Entity
    @Table(name = "mountain")
    public class MountainEntityBase implements Serializable {
        public Integer mountainId = 0;
        public Integer height = 0;
    
        public List<ExplorerEntityBase> explorers = new ArrayList<ExplorerEntityBase>();
    
        @Id
        @GeneratedValue
        @Column(name = "mountain_id")
        public Integer getMountainId() { return mountainId; }
        public void setMountainId(Integer mountainId) { this.mountainId = mountainId; }
    
        @Column(name="height")
        public String getHeight() { return height; }
        public void setHeight(String height) { this.height = height; }
    
        @OneToMany(mappedBy="mountainId")
        public List<ExplorerEntityBase> getExplorers() { return this.explorers; }
        public void setExplorers(List<ExplorerEntityBase> explorers) { this.explorers = explorers; }
    
    }    
    

    .

    @Entity
    public class MountainEntity extends MountainEntityBase implements Serializable {
    
        public List<MountainEntity> allMountainsExploredBy = new ArrayList<MountainEntity>();
    
        @Transient
        public List<MountianEntity> getAllMountainsExploredBy(String explorerName){
            // Implementation 
        }
    }
    

    So any extended class will define only @Transients in its body. But also I want to allow for situations where the child class is empty:

    @Entity
    public class MountainEntity extends MountainEntityBase implements Serializable {
    }
    

    Thanks in advance for any help with this.

  • travega
    travega almost 13 years
    Hi, thanks for your reply. I am more interested in the inheritance aspect than the use of transients at the first pass. Basically I want to also cater for situations where the child class is also empty. (See original post [edited]). Is it possible to do this using the inheritance annotation? Thanks again
  • Bozho
    Bozho almost 13 years
    yes, it is possible. You will just have to specify a discriminator value. I linked the documentation - it's a must-read ;)
  • travega
    travega almost 13 years
    Is there a way to do this without adding a new column to every table in the database?
  • Bozho
    Bozho almost 13 years
    I don't think you should have many tables for inheritance that doesn't add any fields. It can be all in one table (with an additional discriminator column)
  • travega
    travega almost 13 years
    Yeh I was hoping to avoid having to add a new column into every table whose entity I want to extend. You see I want my entities to be clear of any dependencies outside of other entities so that I can move them as a JAR into other modules of my site in the cloud. So I am trying to find a solution that allows me to have Base entities that I can extend in any external modules with only code specific to that module. I doesn't seem as though JPA provides non-polymorphic entity extension. Is that accurate to your knowledge?
  • Bozho
    Bozho almost 13 years
    hibernate needs to have a criteria based on which to instantiate one subclass or another. If there is no discriminator field, hibernate cannot know which of many subclasses you want (or even - do you want to base class or the child)