Is #Inheritance,#DiscriminatorValue,#DiscriminatorColumn applicable to #MappedSuperClass ?
Question is asked because In ORM.XML JPA Specification Entity have attribute :
"inheritance",
"discriminatorValue",
"discriminatorColumn",
but MappedSuperclass does not have .
No, they're not applicable. MappedSuperclass is used for code reuse, and not for entity inheritance. It's only used to share common properties and methods between entities that have, otherwise, nothing in common.
Related
I am working on a project that uses JPA and hibernate, and I've just noticed that the entities don't have any relationship annotations such as #ManyToOne, #OneToOne, etc.
So my question is, does JPA/Hibernate adds a default annotation for each case?
Here is an examples
#Entity
#Table(name = "strategy")
public class Strategy extends TradingEntity implements Serializable {
...
#Valid
private List<Rule> rules;
Does JPA add a #OneToMany annotation by default to this property ?
There are no "default" annotations, but some JPA implementations (e.g the one I've been using, DataNucleus) are intelligent enough to work out that if a field is a Collection of an Entity type then it is a OneToMany/ManyToMany and to default things like fetching and cascading etc. Clearly you cannot assume that your implementation will have this logic so should put what you need (and "JPA" does nothing, it is your implementation that would do it). Clearly also, you can specify the same info in XML so could have no annotations
Is it possible to use #Inheritence Annotation and different strategy at different hierarchy ?
The inheritance strategy and the discriminator column are only specified in the root of an entity class
hierarchy or subhierarchy .
But different strategy allowed ?
Mixing inheritance strategies within a single entity inheritance hierarchy is not a supported JPA configuration. The JPA specification states:
The combination of inheritance strategies within a single entity inheritance hierarchy is not defined by this specification.
I do not think so, please correct me if I am wrong. You can use mixed-inheritance with same hierarchy applying different strategies. Use
#SecondaryTable(
name = "SUBTABLE",
pkJoinColumns = #PrimaryKeyJoinColumn(name = "SUB_TABLE_ID");
before your sub-class definition. Using this, you apply for example SINGLE_TABLE strategy and have separated sub-class table.
I am trying to develop an application with Hibernate and javax.persistence Annotations. I have some troubles in mapping an interface.
I have mapped my interface as #MappedSuperclass and I have already tried to use the attribute targetEntity in my ManyToOne Annotation that referred to the interface and it worked.
The problem is that I would more than one class to act as targetEntity. In particular I'd like that every class that implements my interface, could be recognized as a target entity.
Does anybody knows if it's possible to do it?
I think this
In particular I'd like that every class that implements my interface,
could be recognized as a target entity.
is not possible. Only classes which are annotated with #Entity or which are mapped in an other way (for example with a mapping file) can be persisted.
Also, the Hibernate documentation says:
Note
Annotating interfaces is currently not supported.
See the rather old question Interfaces with hibernate annotations for additional information.
I am using Play Framework 1.2.4 with PostgreSQL and JPA. I would like to have a Model hierarchy and see that there are some alternatives to doing this.
I have a base class (which is abstract) and two concrete classes extending this base class. I don't want to persist this base class while I want to have concrete classes. In the base class, I have another Model classes as properties, in other words, I have #ManyToOne relationships in my base class.
My question is what is the best way of implementing this? Using #MappedSuperclass or #Inheritance with TABLE_PER_CLASS strategy? I am a bit confused as they seem virtually equivalent.
I also have some concerns about querying and performance issues that I might face in future.
MappedSuperClass must be used to inherit properties, associations, and methods.
Entity inheritance must be used when you have an entity, and several sub-entities.
You can tell if you need one or the other by answering this questions: is there some other entity in the model which could have an association with the base class?
If yes, then the base class is in fact an entity, and you should use entity inheritance. If no, then the base class is in fact a class that contains attributes and methods that are common to several unrelated entities, and you should use a mapped superclass.
For example:
You can have several kinds of messages: SMS messages, email messages, or phone messages. And a person has a list of messages. You can also have a reminder linked to a message, regardless of the kind of message. In this case, Message is clearly an entity, and entity inheritance must be used.
All your domain objects could have a creation date, modification date and ID, and you could thus make them inherit from a base AbstractDomainObject class. But no entity will ever have an association to an AbstractDomainObject. It will always be an association to a more specific entity: Customer, Company, whatever. In this case, it makes sense to use a MappedSuperClass.
#MappedSupperclass is different than the #Inheritance annotation.
#MappedSuperclass tells the JPA provider to include the base class persistent properties as if they were declared by the child class extending the superclass annotated with #MappedSuperclass.
However, the inheritance is only visible in the OOP world, since, from a database perspective, there's no indication of the base class. Only the child class entity will have an associated mapped table.
The #Inheritance annotation is meant to materialize the OOP inheritance model in the database table structure. More, you can query a base class annotated with #Inheritance but you can't do that for a base class annotated with #MappedSuperclass.
Now, the reason why you'd want to use the #Inheritance JPA annotation is to implement behavior-driven patterns like the Strategy Pattern.
On the other hand, #MappedSuperclass is just a way to reuse both basic properties, associations, and even the entity #Id using a common base class. Nevertheless, you can achieve almost the same goal using an #Embeddable type. The only major difference is that you can't reuse an #Id definition with #Embeddable, but you can do it with #MappedSuperclass.
So, I'm pretty new to Hibernate and I have a problem.
I have an abstract class (the super-class, class Super), and 5 subclasses which should use the proprieties from the class Super and add a new propriety (a new column)
So how can I do this? Should I extend the class Super from java, or it's enough to join the classes using a JPA annotation.
Here is the second problem. How can I have 1 table for 2 classes.
Someone (smarter than me) told me to use the #JoinTable, but form my searches with google, I think I need to use #Inheritance(strategy=InheritanceStrategy.JOINED)
Can I use the #JoinTable too?
Yours is a case of inheritance:
add the #Inheritance(stretegy=InheritanceStrategy.SINGLE_TABLE) annotation on your Super
add the #DiscriminatorColumn annotation (and setting its attributes name and discriminatorType) (again on the Super)
on each subclass extend the Super, and add the annotation #DiscriminatorValue, with different value for each of the subclasses.
If you are new to Hibernate, you should read its documentation. Inheritance strategies are explained here and using annotations to express inheritance strategy is explained here