Jump to: navigation, search

Difference between revisions of "EclipseLink/UserGuide/JPA/Basic JPA Development/Entities/MappedSuperclass"

(New page: {{EclipseLink_UserGuide |info=y |toc=n |eclipselink=y |eclipselinktype=JPA |api=y |apis= * [http://www.eclipse.org/eclipselink/api/latest/javax/persistence/MappedSuperclass.html @MappedSup...)
 
 
(7 intermediate revisions by the same user not shown)
Line 8: Line 8:
 
* [http://www.eclipse.org/eclipselink/api/latest/javax/persistence/MappedSuperclass.html @MappedSuperclass]
 
* [http://www.eclipse.org/eclipselink/api/latest/javax/persistence/MappedSuperclass.html @MappedSuperclass]
 
* [http://www.eclipse.org/eclipselink/api/latest/javax/persistence/AttributeOverride.html @AttributeOverride]
 
* [http://www.eclipse.org/eclipselink/api/latest/javax/persistence/AttributeOverride.html @AttributeOverride]
 +
* [http://www.eclipse.org/eclipselink/api/latest/javax/persistence/AssociationOverride.html @AssociationOverride]
 
|examples=y
 
|examples=y
 
|example=
 
|example=
* [[EclipseLink/Examples/JPA/Inheritance|How to Define Inheritance]]
 
 
* [[EclipseLink/Examples/JPA/Inheritance#Inheritance_Examples|Advanced Inheritance Examples]]
 
* [[EclipseLink/Examples/JPA/Inheritance#Inheritance_Examples|Advanced Inheritance Examples]]
 
}}
 
}}
  
 
=@MappedSuperclass=
 
=@MappedSuperclass=
You can use the <tt>@Inheritance</tt> annotation or <code><nowiki><inheritance></nowiki></code> XML element to configure how entities with inheritance are persisted.   
+
You can use the <tt>@MappedSuperclass</tt> annotation or <code><nowiki><mapped-superclass></nowiki></code> XML element to define mappings for an abstract or non-persistent superclass, that are inherited by its subclass entities.  A mapped superclass is a special type of class that is not persistent itself, but has subclasses that are persistentA mapped superclass is useful for defined a common persistence superclass that defines common behavior across a set of classes, such as an id or version attributeA mapped superclass should normally be abstract but is not required to be, but cannot have any persistent instances.
JPA defines three inheritance strategies <code>SINGLE_TABLE</code>, <code>JOINED</code>, and <code>TABLE_PER_CLASS</code>By default the <code>SINGLE_TABLE</code> strategy is used and all of the subclasses are persisted in a single table that contains all of the column of all of the subclassesIn addition a discriminator column named <code>DTYPE</code> is required in the table to store the class type.
+
  
For other inheritance strategies see [[#Advanced Inheritance Configuration|Advanced Inheritance Configuration]].
+
Mapped superclasses cannot define a table, but can define mapping for its attributes and other common persistence behavior.  Entities cannot have relationships to mapped superclasses, and mapped superclasses cannot be queried.
  
The <tt>@Inheritance</tt> annotation has the following attributes:
+
The <tt>@MappedSuperclass</tt> annotation does not have any attributes.
<ul>
+
<li> <tt>strategy</tt> – By default, the EclipseLink persistence provider assumes that all the classes in a hierarchy are mapped to a single table differentiated by the discriminator value (see [[#@DiscriminatorValue|@DiscriminatorValue]]) in the table's discriminator column (see [[#@DiscriminatorColumn|@DiscriminatorColumn]]): <tt>InheritanceType.SINGLE_TABLE</tt>.<br>If this is not appropriate for your application or if you must match an existing data model, set <tt>strategy</tt> to the desired <tt>InheritanceType</tt> enumerated type:
+
<ul><li> <tt>SINGLE_TABLE</tt> – all the classes in a hierarchy are mapped to a single table. The table has a discriminator column ([[#@DiscriminatorColumn Attributes|@DiscriminatorColumn]]) whose value ([[#@DiscriminatorValue|@DiscriminatorValue]]) identifies the specific subclass to which the instance that is represented by the row belongs.<br>
+
{{EclipseLink_Note|note=This option provides the best support for both polymorphic relationships between entities and queries that range over the class hierarchy. The disadvantages of this option include the need to make nullable columns that should be <tt>NOT NULL</tt>.}}<br>
+
<li> <tt>TABLE_PER_CLASS</tt> – each class is mapped to a separate table. All properties of the class, including inherited properties, are mapped to columns of the table for the class.
+
{{EclipseLink_Note|note=This option has several limitations when querying or having relationships to the root or branch classes.  Joins to root or branch classes are not supported.}}
+
<li> <tt>JOINED</tt> – the root of the class hierarchy is represented by a single table and each subclass is represented by a separate table. Each subclass table contains only those fields that are specific to the subclass (not inherited from its superclass) and primary key columns that serve as foreign keys to the primary keys of the superclass table.  The join from the primary table to the subclass table can be configured using the <code>@PrimaryKeyJoinColumn</code>, see [[EclipseLink/UserGuide/JPA/Basic JPA Development/Entities/SecondaryTable|SecondaryTable]] for more info.  If you have multiple levels of inheritance, each subclass table should join with the root table, and the discriminator column is only defined once in the root table.
+
</ul></ul>
+
  
 
{{EclipseLink_Spec|section=Section 2.1.9 "Inheritance"}}
 
{{EclipseLink_Spec|section=Section 2.1.9 "Inheritance"}}
{{EclipseLink_Spec|section=Section 9.1.29 "Inheritance Annotation"}}
+
{{EclipseLink_Spec|section=Section 11.1.34 "MappedSuperclass Annotation"}}
  
===@DiscriminatorColumn===
+
===@AttributeOverride===
You can use the <tt>@DiscriminatorColumn</tt> annotation or <code><nowiki><discriminator-column></nowiki></code> XML element to configure the name or type of the inheritance discriminator column.  The discriminator column is required for <code>SINGLE_TABLE</code> and <code>JOINED</code> inheritance and stores the associated entity type for the rowThe default name for the discriminator column is <code>DTYPE</code>.  JPA only allows String or Integer values for discriminators.  Through the EclipseLink API, it is possible to use other discriminator types, and it is possible to not have a discriminator, or use custom discriminator, see [[#Advanced Inheritance Configuration|Advanced Inheritance Configuration]].
+
You can use the <tt>@AttributeOverride</tt> and <tt>@AttributeOverrides</tt> annotations, or <code><nowiki><attribute-override></nowiki></code> XML element to override the column for a basic attribute in a mapped superclassThis allows for the column name to be different in each subclass.
  
 
{{EclipseLink_AttributeTable
 
{{EclipseLink_AttributeTable
|caption=@DiscriminatorColumn Attributes
+
|caption=@AttributeOverride Attributes
 
|content=<tr>
 
|content=<tr>
 
  <td>'''<tt>name</tt>'''</td>
 
  <td>'''<tt>name</tt>'''</td>
  <td>The name of column to be used to store the class discriminator value.
+
  <td>The name of the attribute.
  <td><code>DTYPE</code></td>
+
  <td></td>
  <td>No</td>
+
  <td>Yes</td>
 
</tr>
 
</tr>
 
<tr>
 
<tr>
  <td>'''<tt>discriminatorType</tt>'''</td>
+
  <td>'''<tt>column</tt>'''</td>
  <td>The type of the discriminator value, defined in <code>DiscriminatorType</code>, one of <code>STRING</code>, <code>INTEGER</code>, and <code>CHAR</code>.
+
  <td>The column in the subclass table.
  <td><code>STRING</code></td>
+
  <td><code>column defined in mapped superclass</code></td>
 
  <td>No</td>
 
  <td>No</td>
 +
</tr>
 +
}}
 +
{{EclipseLink_Spec|section=Section 11.1.4 "AttributeOverride Annotation"}}
 +
 +
===@AssociationOverride===
 +
You can use the <tt>@AssociationOverride</tt> and <tt>@AssociationOverrides</tt> annotations, or <code><nowiki><association-override></nowiki></code> XML element to override the join column or join table for a relationship attribute in a mapped superclass.  This allows for the join column name or join table to be different in each subclass.
 +
 +
{{EclipseLink_AttributeTable
 +
|caption=@AssociationOverrideAttributes
 +
|content=<tr>
 +
<td>'''<tt>name</tt>'''</td>
 +
<td>The name of the attribute.
 +
<td></td>
 +
<td>Yes</td>
 
</tr>
 
</tr>
 
<tr>
 
<tr>
  <td>'''<tt>columnDefinition</tt>'''</td>
+
  <td>'''<tt>joinColumn</tt>'''</td>
  <td>Optional column description for use with DDL generation.</td>
+
  <td>The join column in the subclass table.
  <td>generated base on <tt>discriminatorType</tt></td>
+
  <td><code>join column defined in mapped superclass</code></td>
 
  <td>No</td>
 
  <td>No</td>
 
</tr>
 
</tr>
 
<tr>
 
<tr>
  <td>'''<tt>length</tt>'''</td>
+
  <td>'''<tt>joinTable</tt>'''</td>
  <td>The size of the column for DDL generationOnly relevant for <code>STRING</code> types.</td>
+
  <td>The join table for the subclass.
<td>31</td>
+
  <td><code>join table defined in mapped superclass</code></td>
 
  <td>No</td>
 
  <td>No</td>
 
</tr>
 
</tr>
 
}}
 
}}
{{EclipseLink_Spec|section=Section 11.1.10 "DiscriminatorColumn Annotation"}}
+
{{EclipseLink_Spec|section=Section 11.1.2 "AssociationOverride Annotation"}}
  
===@DiscriminatorValue===
+
The following example shows usages of a generic persistence mapped superclass.
You can use the <tt>@DiscriminatorValue</tt> annotation or <code><nowiki><discriminator-value></nowiki></code> XML element to configure the value of the inheritance discriminator.  The discriminator value can be specified in each non-abstract class in the inheritance hierarchy.  By default the discriminator value is the entity's name, which defaults to its unprefixed class name.  The discriminator value is always specified as a String, but is converted to the discriminator column type.
+
  
 
+
<span id="Example: @MappedSuperClass"></span>
The following examples shows usages of the three different inheritance strategies for mapping an <code>Account</code> hierarchy.
+
======''Example: Using @MappedSuperClass annotation''======
 
+
<span id="Example: @Inheritance"></span>
+
======''Example: Using <code>SINGLE_TABLE</code> with @Inheritance annotation''======
+
<source lang="SQL">
+
create table ACCOUNT (ID NUMBER, ACCOUNT_TYPE VARCHAR(31), BALANCE NUMBER, INTERESTRATE NUMBER, RETURNCHECKS BOOLEAN)
+
</source>
+
  
 
<source lang="java">
 
<source lang="java">
@Entity
+
@MappedSuperclass
@Table(name="ACCOUNT")
+
public abstract class PersistentObject implements Serializable {
@Inheritance(strategy=InheritanceType.SINGLE_TABLE)
+
@DiscriminatorColumn(name="ACCOUNT_TYPE")
+
public abstract class Account implements Serializable {
+
 
     @Id
 
     @Id
 
     private Long id;
 
     private Long id;
     @Basic
+
     @Version
     private BigDecimal balance;
+
     private Long version;
 
     ...
 
     ...
 
}
 
}
Line 93: Line 88:
 
<source lang="java">
 
<source lang="java">
 
@Entity
 
@Entity
@DiscriminatorValue("SAVINGS")
+
@Table("EMP")
public class SavingAccount extends Account {
+
public class Employee extends PersistentObject {
 
     @Basic
 
     @Basic
     private BigDecimal interestRate;
+
     private String name;
 +
    ...
 
}
 
}
 
</source>
 
</source>
Line 102: Line 98:
 
<source lang="java">
 
<source lang="java">
 
@Entity
 
@Entity
@DiscriminatorValue("CHECKING")
+
@Table("PROJECT")
public class CheckingAccount extends Account {
+
@AttributeOverride(name="id" column=@Column(name="PROJ_ID"))
 +
public class Project extends PersistentObject {
 
     @Basic
 
     @Basic
     private boolean returnChecks;
+
     private String name;
 +
    ...
 
}
 
}
 
</source>
 
</source>
  
======''Example: Using <code>SINGLE_TABLE</code> with <code><nowiki><inheritance></nowiki></code> XML''======
+
======''Example: Using <code><nowiki><mapped-superclass></nowiki></code> XML''======
  
 
<source lang="xml">
 
<source lang="xml">
<entity class="Account">
+
<mapped-superclass class="PersistentObject">
    <table name="ACCOUNT"/>
+
    <inheritance strategy="SINGLE_TABLE"/>
+
    <discriminator-column name="ACCOUNT_TYPE"/>
+
 
     <attributes>
 
     <attributes>
 
         <id name="id"/>
 
         <id name="id"/>
         <basic name="balance"/>
+
         <version name="version"/>
 
     </attributes>
 
     </attributes>
</entity>
+
</mapped-superclass>
</source>
+
<entity class="Employee">
<source lang="xml">
+
    <table name="EMP">
 
+
<entity class="SavingAccount">
+
    <discriminator-value>SAVINGS</discriminator-value>
+
 
     <attributes>
 
     <attributes>
         <basic name="interestRate"/>
+
         <basic name="name"/>
 +
        ...
 
     </attributes>
 
     </attributes>
 
</entity>
 
</entity>
</source>
+
<entity class="Project">
 
+
    <table name="PROJECT">
<source lang="xml">
+
    <attribute-override name="id">
<entity class="CheckingAccount">
+
        <column name="PROJ_ID"/>
    <discriminator-value>CHECKING</discriminator-value>
+
    </attribute-override>
 
     <attributes>
 
     <attributes>
         <basic name="returnChecks"/>
+
         ...
 
     </attributes>
 
     </attributes>
 
</entity>
 
</entity>
Line 144: Line 137:
 
{{EclipseLink_JPA
 
{{EclipseLink_JPA
 
|previous=[[EclipseLink/UserGuide/JPA/Basic JPA Development/Entities/Inheritance|@Inheritance]]
 
|previous=[[EclipseLink/UserGuide/JPA/Basic JPA Development/Entities/Inheritance|@Inheritance]]
|next=    [[EclipseLink/UserGuide/JPA/Basic JPA Development/Mapping|Configuring Mappings]]
+
|next=    [[EclipseLink/UserGuide/JPA/Basic JPA Development/Entities/Embeddable|@Embeddable]]
 
|up=      [[EclipseLink/UserGuide/JPA/Basic JPA Development/Entities/Creating_and_Configuring_Entities|Configuring Entities]]
 
|up=      [[EclipseLink/UserGuide/JPA/Basic JPA Development/Entities/Creating_and_Configuring_Entities|Configuring Entities]]
 
|version=2.2.0 DRAFT}}
 
|version=2.2.0 DRAFT}}

Latest revision as of 11:53, 28 July 2011

EclipseLink JPA


@MappedSuperclass

You can use the @MappedSuperclass annotation or <mapped-superclass> XML element to define mappings for an abstract or non-persistent superclass, that are inherited by its subclass entities. A mapped superclass is a special type of class that is not persistent itself, but has subclasses that are persistent. A mapped superclass is useful for defined a common persistence superclass that defines common behavior across a set of classes, such as an id or version attribute. A mapped superclass should normally be abstract but is not required to be, but cannot have any persistent instances.

Mapped superclasses cannot define a table, but can define mapping for its attributes and other common persistence behavior. Entities cannot have relationships to mapped superclasses, and mapped superclasses cannot be queried.

The @MappedSuperclass annotation does not have any attributes.

Elug javaspec icon.gif

For more information, see Section 2.1.9 "Inheritance" in the JPA Specification.

Elug javaspec icon.gif

For more information, see Section 11.1.34 "MappedSuperclass Annotation" in the JPA Specification.

@AttributeOverride

You can use the @AttributeOverride and @AttributeOverrides annotations, or <attribute-override> XML element to override the column for a basic attribute in a mapped superclass. This allows for the column name to be different in each subclass.

@AttributeOverride Attributes
Attribute Description Default Required?
name The name of the attribute. Yes
column The column in the subclass table. column defined in mapped superclass No
Elug javaspec icon.gif

For more information, see Section 11.1.4 "AttributeOverride Annotation" in the JPA Specification.

@AssociationOverride

You can use the @AssociationOverride and @AssociationOverrides annotations, or <association-override> XML element to override the join column or join table for a relationship attribute in a mapped superclass. This allows for the join column name or join table to be different in each subclass.

@AssociationOverrideAttributes
Attribute Description Default Required?
name The name of the attribute. Yes
joinColumn The join column in the subclass table. join column defined in mapped superclass No
joinTable The join table for the subclass. join table defined in mapped superclass No
Elug javaspec icon.gif

For more information, see Section 11.1.2 "AssociationOverride Annotation" in the JPA Specification.

The following example shows usages of a generic persistence mapped superclass.

Example: Using @MappedSuperClass annotation
@MappedSuperclass
public abstract class PersistentObject implements Serializable {
    @Id
    private Long id;
    @Version
    private Long version;
    ...
}
@Entity
@Table("EMP")
public class Employee extends PersistentObject {
    @Basic
    private String name;
    ...
}
@Entity
@Table("PROJECT")
@AttributeOverride(name="id" column=@Column(name="PROJ_ID"))
public class Project extends PersistentObject {
    @Basic
    private String name;
    ...
}
Example: Using <mapped-superclass> XML
<mapped-superclass class="PersistentObject">
    <attributes>
        <id name="id"/>
        <version name="version"/>
    </attributes>
</mapped-superclass>
<entity class="Employee">
    <table name="EMP">
    <attributes>
        <basic name="name"/>
        ...
    </attributes>
</entity>
<entity class="Project">
    <table name="PROJECT">
    <attribute-override name="id">
        <column name="PROJ_ID"/>
    </attribute-override>
    <attributes>
        ...
    </attributes>
</entity>


Eclipselink-logo.gif
Version: 2.2.0 DRAFT
Other versions...