diff --git a/documentation/manual/src/main/docbook/en-US/content/basic_mapping.xml b/documentation/manual/src/main/docbook/en-US/content/basic_mapping.xml
index 051cf29fe1..bdaf0f216e 100644
--- a/documentation/manual/src/main/docbook/en-US/content/basic_mapping.xml
+++ b/documentation/manual/src/main/docbook/en-US/content/basic_mapping.xml
@@ -210,345 +210,6 @@ public class Dog { ... }
affect the database schemas exported by the schema export tool (for
example, the not-null attribute).
-
- Some hbm.xml specificities
-
- The hbm.xml structure has some specificities naturally not present
- when using annotations, let's describe them briefly.
-
-
- Doctype
-
- All XML mappings should declare the doctype shown. The actual
- DTD can be found at the URL above, in the directory
- hibernate-x.x.x/src/org/hibernate , or in
- hibernate3.jar. Hibernate will always look for the
- DTD in its classpath first. If you experience lookups of the DTD using
- an Internet connection, check the DTD declaration against the contents
- of your classpath.
-
-
- EntityResolver
-
- Hibernate will first attempt to resolve DTDs in its classpath.
- It does this is by registering a custom
- org.xml.sax.EntityResolver implementation with
- the SAXReader it uses to read in the xml files. This custom
- EntityResolver recognizes two different systemId
- namespaces:
-
-
-
- a hibernate namespace is recognized
- whenever the resolver encounters a systemId starting with
- http://hibernate.sourceforge.net/. The
- resolver attempts to resolve these entities via the classloader
- which loaded the Hibernate classes.
-
-
-
- a user namespace is recognized whenever
- the resolver encounters a systemId using a
- classpath:// URL protocol. The resolver will
- attempt to resolve these entities via (1) the current thread
- context classloader and (2) the classloader which loaded the
- Hibernate classes.
-
-
-
- The following is an example of utilizing user
- namespacing:
-
-
-
-
-
- Where types.xml is a resource in the
- your.domain package and contains a custom typedef.
-
-
-
-
- Hibernate-mapping
-
- This element has several optional attributes. The
- schema and catalog attributes
- specify that tables referred to in this mapping belong to the named
- schema and/or catalog. If they are specified, tablenames will be
- qualified by the given schema and catalog names. If they are missing,
- tablenames will be unqualified. The default-cascade
- attribute specifies what cascade style should be assumed for
- properties and collections that do not specify a
- cascade attribute. By default, the
- auto-import attribute allows you to use unqualified
- class names in the query language.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- <hibernate-mapping
- schema="schemaName"
- catalog="catalogName"
- default-cascade="cascade_style"
- default-access="field|property|ClassName"
- default-lazy="true|false"
- auto-import="true|false"
- package="package.name"
- />
-
-
-
- schema (optional): the name of a
- database schema.
-
-
-
- catalog (optional): the name of a
- database catalog.
-
-
-
- default-cascade (optional - defaults to
- none): a default cascade style.
-
-
-
- default-access (optional - defaults to
- property): the strategy Hibernate should use
- for accessing all properties. It can be a custom implementation
- of PropertyAccessor.
-
-
-
- default-lazy (optional - defaults to
- true): the default value for unspecified
- lazy attributes of class and collection
- mappings.
-
-
-
- auto-import (optional - defaults to
- true): specifies whether we can use
- unqualified class names of classes in this mapping in the query
- language.
-
-
-
- package (optional): specifies a package
- prefix to use for unqualified class names in the mapping
- document.
-
-
-
-
- If you have two persistent classes with the same unqualified
- name, you should set auto-import="false". An
- exception will result if you attempt to assign two classes to the same
- "imported" name.
-
- The hibernate-mapping element allows you to
- nest several persistent <class> mappings, as
- shown above. It is, however, good practice (and expected by some
- tools) to map only a single persistent class, or a single class
- hierarchy, in one mapping file and name it after the persistent
- superclass. For example, Cat.hbm.xml,
- Dog.hbm.xml, or if using inheritance,
- Animal.hbm.xml.
-
-
-
- Key
-
- The <key> element is featured a few
- times within this guide. It appears anywhere the parent mapping
- element defines a join to a new table that references the primary key
- of the original table. It also defines the foreign key in the joined
- table:
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- <key
- column="columnname"
- on-delete="noaction|cascade"
- property-ref="propertyName"
- not-null="true|false"
- update="true|false"
- unique="true|false"
-/>
-
-
-
- column (optional): the name of the
- foreign key column. This can also be specified by nested
- <column> element(s).
-
-
-
- on-delete (optional - defaults to
- noaction): specifies whether the foreign key
- constraint has database-level cascade delete enabled.
-
-
-
- property-ref (optional): specifies that
- the foreign key refers to columns that are not the primary key
- of the original table. It is provided for legacy data.
-
-
-
- not-null (optional): specifies that the
- foreign key columns are not nullable. This is implied whenever
- the foreign key is also part of the primary key.
-
-
-
- update (optional): specifies that the
- foreign key should never be updated. This is implied whenever
- the foreign key is also part of the primary key.
-
-
-
- unique (optional): specifies that the
- foreign key should have a unique constraint. This is implied
- whenever the foreign key is also the primary key.
-
-
-
-
- For systems where delete performance is important, we recommend
- that all keys should be defined
- on-delete="cascade". Hibernate uses a
- database-level ON CASCADE DELETE constraint,
- instead of many individual DELETE statements. Be
- aware that this feature bypasses Hibernate's usual optimistic locking
- strategy for versioned data.
-
- The not-null and update
- attributes are useful when mapping a unidirectional one-to-many
- association. If you map a unidirectional one-to-many association to a
- non-nullable foreign key, you must declare the
- key column using <key
- not-null="true">.
-
-
-
- Import
-
- If your application has two persistent classes with the same
- name, and you do not want to specify the fully qualified package name
- in Hibernate queries, classes can be "imported" explicitly, rather
- than relying upon auto-import="true". You can also
- import classes and interfaces that are not explicitly mapped:
-
- <import class="java.lang.Object" rename="Universe"/>
-
-
-
-
-
-
-
-
- <import
- class="ClassName"
- rename="ShortName"
-/>
-
-
-
- class: the fully qualified class name
- of any Java class.
-
-
-
- rename (optional - defaults to the
- unqualified class name): a name that can be used in the query
- language.
-
-
-
-
-
- This feature is unique to hbm.xml and is not supported in
- annotations.
-
-
-
-
- Column and formula elements
-
- Mapping elements which accept a column
- attribute will alternatively accept a
- <column> subelement. Likewise,
- <formula> is an alternative to the
- formula attribute. For example:
-
- <column
- name="column_name"
- length="N"
- precision="N"
- scale="N"
- not-null="true|false"
- unique="true|false"
- unique-key="multicolumn_unique_key_name"
- index="index_name"
- sql-type="sql_type_name"
- check="SQL expression"
- default="SQL expression"
- read="SQL expression"
- write="SQL expression"/>
-
- <formula>SQL expression</formula>
-
- Most of the attributes on column provide a
- means of tailoring the DDL during automatic schema generation. The
- read and write attributes allow
- you to specify custom SQL that Hibernate will use to access the
- column's value. For more on this, see the discussion of column read and write
- expressions.
-
- The column and formula
- elements can even be combined within the same property or association
- mapping to express, for example, exotic join conditions.
-
- <many-to-one name="homeAddress" class="Address"
- insert="false" update="false">
- <column name="person_id" not-null="true" length="10"/>
- <formula>'MAILING'</formula>
-</many-to-one>
-
-
-
Entity
@@ -2399,803 +2060,6 @@ public class Customer implements Serializable {
-
- Inheritance strategy
-
- Java is a language supporting polymorphism: a class can inherit
- from another. Several strategies are possible to persist a class
- hierarchy:
-
-
-
- Single table per class hierarchy strategy: a single table
- hosts all the instances of a class hierarchy
-
-
-
- Joined subclass strategy: one table per class and subclass is
- present and each table persist the properties specific to a given
- subclass. The state of the entity is then stored in its
- corresponding class table and all its superclasses
-
-
-
- Table per class strategy: one table per concrete class and
- subclass is present and each table persist the properties of the
- class and its superclasses. The state of the entity is then stored
- entirely in the dedicated table for its class.
-
-
-
-
- Single table per class hierarchy strategy
-
- With this approach the properties of all the subclasses in a
- given mapped class hierarchy are stored in a single table.
-
- Each subclass declares its own persistent properties and
- subclasses. Version and id properties are assumed to be inherited from
- the root class. Each subclass in a hierarchy must define a unique
- discriminator value. If this is not specified, the fully qualified
- Java class name is used.
-
- @Entity
-@Inheritance(strategy=InheritanceType.SINGLE_TABLE)
-@DiscriminatorColumn(
- name="planetype",
- discriminatorType=DiscriminatorType.STRING
-)
-@DiscriminatorValue("Plane")
-public class Plane { ... }
-
-@Entity
-@DiscriminatorValue("A320")
-public class A320 extends Plane { ... }
-
- In hbm.xml, for the table-per-class-hierarchy mapping strategy,
- the <subclass> declaration is used. For
- example:
-
-
-
-
-
-
-
-
-
-
-
-
- <subclass
- name="ClassName"
- discriminator-value="discriminator_value"
- proxy="ProxyInterface"
- lazy="true|false"
- dynamic-update="true|false"
- dynamic-insert="true|false"
- entity-name="EntityName"
- node="element-name"
- extends="SuperclassName">
-
- <property .... />
- .....
-</subclass>
-
-
-
- name: the fully qualified class name of
- the subclass.
-
-
-
- discriminator-value (optional -
- defaults to the class name): a value that distinguishes
- individual subclasses.
-
-
-
- proxy (optional): specifies a class or
- interface used for lazy initializing proxies.
-
-
-
- lazy (optional - defaults to
- true): setting
- lazy="false" disables the use of lazy
- fetching.
-
-
-
-
- For information about inheritance mappings see .
-
-
- Discriminator
-
- Discriminators are required for polymorphic persistence using
- the table-per-class-hierarchy mapping strategy. It declares a
- discriminator column of the table. The discriminator column contains
- marker values that tell the persistence layer what subclass to
- instantiate for a particular row. A restricted set of types can be
- used: string, character,
- integer, byte,
- short, boolean,
- yes_no, true_false.
-
- Use the @DiscriminatorColumn to define
- the discriminator column as well as the discriminator type.
- Alternatively, you can also use
- @DiscriminatorFormula to express in SQL what
- would be in a virtual discriminator column. This is particularly
- handy when the discriminator value can be extracted from one or more
- columns of the table. Both
- @DiscriminatorColumn and
- @DiscriminatorFormula are to be set on the
- root entity (once per persisted hierarchy).
-
- Finally, use @DiscriminatorValue on
- each class of the hierarchy to specify the value stored in the
- discriminator column for a given entity. If you do not set
- @DiscriminatorValue on a class, the fully
- qualified class name is used.
-
- @Entity
-@Inheritance(strategy=InheritanceType.SINGLE_TABLE)
-@DiscriminatorColumn(
- name="planetype",
- discriminatorType=DiscriminatorType.STRING
-)
-@DiscriminatorValue("Plane")
-public class Plane { ... }
-
-@Entity
-@DiscriminatorValue("A320")
-public class A320 extends Plane { ... }
-
- In hbm.xml, the <discriminator>
- element is used to define the discriminator column or
- formula:
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- <discriminator
- column="discriminator_column"
- type="discriminator_type"
- force="true|false"
- insert="true|false"
- formula="arbitrary sql expression"
-/>
-
-
-
- column (optional - defaults to
- class): the name of the discriminator
- column.
-
-
-
- type (optional - defaults to
- string): a name that indicates the
- Hibernate type
-
-
-
- force (optional - defaults to
- false): "forces" Hibernate to specify the
- allowed discriminator values, even when retrieving all
- instances of the root class.
-
-
-
- insert (optional - defaults to
- true): set this to false
- if your discriminator column is also part of a mapped
- composite identifier. It tells Hibernate not to include the
- column in SQL INSERTs.
-
-
-
- formula (optional): an arbitrary SQL
- expression that is executed when a type has to be evaluated.
- It allows content-based discrimination.
-
-
-
-
- Actual values of the discriminator column are specified by the
- discriminator-value attribute of the
- <class> and
- <subclass> elements.
-
- The force attribute is only useful if the
- table contains rows with "extra" discriminator values that are not
- mapped to a persistent class. This will not usually be the
- case.
-
- The formula attribute allows you to declare
- an arbitrary SQL expression that will be used to evaluate the type
- of a row. For example:
-
- <discriminator
- formula="case when CLASS_TYPE in ('a', 'b', 'c') then 0 else 1 end"
- type="integer"/>
-
-
-
-
- Joined subclass strategy
-
- Each subclass can also be mapped to its own table. This is
- called the table-per-subclass mapping strategy. An inherited state is
- retrieved by joining with the table of the superclass. A discriminator
- column is not required for this mapping strategy. Each subclass must,
- however, declare a table column holding the object identifier. The
- primary key of this table is also a foreign key to the superclass
- table and described by the
- @PrimaryKeyJoinColumns or the
- <key> element.
-
- @Entity @Table(name="CATS")
-@Inheritance(strategy=InheritanceType.JOINED)
-public class Cat implements Serializable {
- @Id @GeneratedValue(generator="cat-uuid")
- @GenericGenerator(name="cat-uuid", strategy="uuid")
- String getId() { return id; }
-
- ...
-}
-
-@Entity @Table(name="DOMESTIC_CATS")
-@PrimaryKeyJoinColumn(name="CAT")
-public class DomesticCat extends Cat {
- public String getName() { return name; }
-}
-
-
- The table name still defaults to the non qualified class name.
- Also if @PrimaryKeyJoinColumn is not set, the
- primary key / foreign key columns are assumed to have the same names
- as the primary key columns of the primary table of the
- superclass.
-
-
- In hbm.xml, use the <joined-subclass>
- element. For example:
-
-
-
-
-
-
-
-
-
-
-
-
- <joined-subclass
- name="ClassName"
- table="tablename"
- proxy="ProxyInterface"
- lazy="true|false"
- dynamic-update="true|false"
- dynamic-insert="true|false"
- schema="schema"
- catalog="catalog"
- extends="SuperclassName"
- persister="ClassName"
- subselect="SQL expression"
- entity-name="EntityName"
- node="element-name">
-
- <key .... >
-
- <property .... />
- .....
-</joined-subclass>
-
-
-
- name: the fully qualified class name of
- the subclass.
-
-
-
- table: the name of the subclass
- table.
-
-
-
- proxy (optional): specifies a class or
- interface to use for lazy initializing proxies.
-
-
-
- lazy (optional, defaults to
- true): setting
- lazy="false" disables the use of lazy
- fetching.
-
-
-
-
- Use the <key> element to declare the
- primary key / foreign key column. The mapping at the start of the
- chapter would then be re-written as:
-
- <?xml version="1.0"?>
-<!DOCTYPE hibernate-mapping PUBLIC
- "-//Hibernate/Hibernate Mapping DTD//EN"
- "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
-
-<hibernate-mapping package="eg">
-
- <class name="Cat" table="CATS">
- <id name="id" column="uid" type="long">
- <generator class="hilo"/>
- </id>
- <property name="birthdate" type="date"/>
- <property name="color" not-null="true"/>
- <property name="sex" not-null="true"/>
- <property name="weight"/>
- <many-to-one name="mate"/>
- <set name="kittens">
- <key column="MOTHER"/>
- <one-to-many class="Cat"/>
- </set>
- <joined-subclass name="DomesticCat" table="DOMESTIC_CATS">
- <key column="CAT"/>
- <property name="name" type="string"/>
- </joined-subclass>
- </class>
-
- <class name="eg.Dog">
- <!-- mapping for Dog could go here -->
- </class>
-
-</hibernate-mapping>
-
- For information about inheritance mappings see .
-
-
-
- Table per class strategy
-
- A third option is to map only the concrete classes of an
- inheritance hierarchy to tables. This is called the
- table-per-concrete-class strategy. Each table defines all persistent
- states of the class, including the inherited state. In Hibernate, it
- is not necessary to explicitly map such inheritance hierarchies. You
- can map each class as a separate entity root. However, if you wish use
- polymorphic associations (e.g. an association to the superclass of
- your hierarchy), you need to use the union subclass mapping.
-
- @Entity
-@Inheritance(strategy = InheritanceType.TABLE_PER_CLASS)
-public class Flight implements Serializable { ... }
-
- Or in hbm.xml:
-
-
-
-
-
-
-
-
-
-
-
-
- <union-subclass
- name="ClassName"
- table="tablename"
- proxy="ProxyInterface"
- lazy="true|false"
- dynamic-update="true|false"
- dynamic-insert="true|false"
- schema="schema"
- catalog="catalog"
- extends="SuperclassName"
- abstract="true|false"
- persister="ClassName"
- subselect="SQL expression"
- entity-name="EntityName"
- node="element-name">
-
- <property .... />
- .....
-</union-subclass>
-
-
-
- name: the fully qualified class name of
- the subclass.
-
-
-
- table: the name of the subclass
- table.
-
-
-
- proxy (optional): specifies a class or
- interface to use for lazy initializing proxies.
-
-
-
- lazy (optional, defaults to
- true): setting
- lazy="false" disables the use of lazy
- fetching.
-
-
-
-
- No discriminator column or key column is required for this
- mapping strategy.
-
- For information about inheritance mappings see .
-
-
-
- Inherit properties from superclasses
-
- This is sometimes useful to share common properties through a
- technical or a business superclass without including it as a regular
- mapped entity (ie no specific table for this entity). For that purpose
- you can map them as @MappedSuperclass.
-
- @MappedSuperclass
-public class BaseEntity {
- @Basic
- @Temporal(TemporalType.TIMESTAMP)
- public Date getLastUpdate() { ... }
- public String getLastUpdater() { ... }
- ...
-}
-
-@Entity class Order extends BaseEntity {
- @Id public Integer getId() { ... }
- ...
-}
-
- In database, this hierarchy will be represented as an
- Order table having the id,
- lastUpdate and lastUpdater
- columns. The embedded superclass property mappings are copied into
- their entity subclasses. Remember that the embeddable superclass is
- not the root of the hierarchy though.
-
-
- Properties from superclasses not mapped as
- @MappedSuperclass are ignored.
-
-
-
- The default access type (field or methods) is used, unless you
- use the @Access annotation.
-
-
-
- The same notion can be applied to
- @Embeddable objects to persist properties from
- their superclasses. You also need to use
- @MappedSuperclass to do that (this should not be
- considered as a standard EJB3 feature though)
-
-
-
- It is allowed to mark a class as
- @MappedSuperclass in the middle of the mapped
- inheritance hierarchy.
-
-
-
- Any class in the hierarchy non annotated with
- @MappedSuperclass nor @Entity
- will be ignored.
-
-
- You can override columns defined in entity superclasses at the
- root entity level using the @AttributeOverride
- annotation.
-
- @MappedSuperclass
-public class FlyingObject implements Serializable {
-
- public int getAltitude() {
- return altitude;
- }
-
- @Transient
- public int getMetricAltitude() {
- return metricAltitude;
- }
-
- @ManyToOne
- public PropulsionType getPropulsion() {
- return metricAltitude;
- }
- ...
-}
-
-@Entity
-@AttributeOverride( name="altitude", column = @Column(name="fld_altitude") )
-@AssociationOverride(
- name="propulsion",
- joinColumns = @JoinColumn(name="fld_propulsion_fk")
-)
-public class Plane extends FlyingObject {
- ...
-}
-
- The altitude property will be persisted in an
- fld_altitude column of table
- Plane and the propulsion association will be
- materialized in a fld_propulsion_fk foreign key
- column.
-
- You can define @AttributeOverride(s) and
- @AssociationOverride(s) on
- @Entity classes,
- @MappedSuperclass classes and properties pointing
- to an @Embeddable object.
-
- In hbm.xml, simply map the properties of the superclass in the
- <class> element of the entity that needs to
- inherit them.
-
-
-
- Mapping one entity to several tables
-
- While not recommended for a fresh schema, some legacy databases
- force your to map a single entity on several tables.
-
- Using the @SecondaryTable or
- @SecondaryTables class level annotations. To
- express that a column is in a particular table, use the
- table parameter of @Column or
- @JoinColumn.
-
- @Entity
-@Table(name="MainCat")
-@SecondaryTables({
- @SecondaryTable(name="Cat1", pkJoinColumns={
- @PrimaryKeyJoinColumn(name="cat_id", referencedColumnName="id")
- ),
- @SecondaryTable(name="Cat2", uniqueConstraints={@UniqueConstraint(columnNames={"storyPart2"})})
-})
-public class Cat implements Serializable {
-
- private Integer id;
- private String name;
- private String storyPart1;
- private String storyPart2;
-
- @Id @GeneratedValue
- public Integer getId() {
- return id;
- }
-
- public String getName() {
- return name;
- }
-
- @Column(table="Cat1")
- public String getStoryPart1() {
- return storyPart1;
- }
-
- @Column(table="Cat2")
- public String getStoryPart2() {
- return storyPart2;
- }
-}
-
- In this example, name will be in
- MainCat. storyPart1 will be in
- Cat1 and storyPart2 will be in
- Cat2. Cat1 will be joined to
- MainCat using the cat_id as a
- foreign key, and Cat2 using id
- (ie the same column name, the MainCat id column
- has). Plus a unique constraint on storyPart2 has
- been set.
-
- There is also additional tuning accessible via the
- @org.hibernate.annotations.Table
- annotation:
-
-
-
- fetch: If set to JOIN, the default,
- Hibernate will use an inner join to retrieve a secondary table
- defined by a class or its superclasses and an outer join for a
- secondary table defined by a subclass. If set to
- SELECT then Hibernate will use a sequential
- select for a secondary table defined on a subclass, which will be
- issued only if a row turns out to represent an instance of the
- subclass. Inner joins will still be used to retrieve a secondary
- defined by the class and its superclasses.
-
-
-
- inverse: If true, Hibernate will not try
- to insert or update the properties defined by this join. Default
- to false.
-
-
-
- optional: If enabled (the default),
- Hibernate will insert a row only if the properties defined by this
- join are non-null and will always use an outer join to retrieve
- the properties.
-
-
-
- foreignKey: defines the Foreign Key name
- of a secondary table pointing back to the primary table.
-
-
-
- Make sure to use the secondary table name in the
- appliesto property
-
- @Entity
-@Table(name="MainCat")
-@SecondaryTable(name="Cat1")
-@org.hibernate.annotations.Table(
- appliesTo="Cat1",
- fetch=FetchMode.SELECT,
- optional=true)
-public class Cat implements Serializable {
-
- private Integer id;
- private String name;
- private String storyPart1;
- private String storyPart2;
-
- @Id @GeneratedValue
- public Integer getId() {
- return id;
- }
-
- public String getName() {
- return name;
- }
-
- @Column(table="Cat1")
- public String getStoryPart1() {
- return storyPart1;
- }
-
- @Column(table="Cat2")
- public String getStoryPart2() {
- return storyPart2;
- }
-}
-
- In hbm.xml, use the <join>
- element.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- <join
- table="tablename"
- schema="owner"
- catalog="catalog"
- fetch="join|select"
- inverse="true|false"
- optional="true|false">
-
- <key ... />
-
- <property ... />
- ...
-</join>
-
-
-
- table: the name of the joined
- table.
-
-
-
- schema (optional): overrides the schema
- name specified by the root
- <hibernate-mapping> element.
-
-
-
- catalog (optional): overrides the
- catalog name specified by the root
- <hibernate-mapping> element.
-
-
-
- fetch (optional - defaults to
- join): if set to join, the
- default, Hibernate will use an inner join to retrieve a
- <join> defined by a class or its
- superclasses. It will use an outer join for a
- <join> defined by a subclass. If set to
- select then Hibernate will use a sequential
- select for a <join> defined on a
- subclass. This will be issued only if a row represents an
- instance of the subclass. Inner joins will still be used to
- retrieve a <join> defined by the class
- and its superclasses.
-
-
-
- inverse (optional - defaults to
- false): if enabled, Hibernate will not insert
- or update the properties defined by this join.
-
-
-
- optional (optional - defaults to
- false): if enabled, Hibernate will insert a
- row only if the properties defined by this join are non-null. It
- will always use an outer join to retrieve the properties.
-
-
-
-
- For example, address information for a person can be mapped to a
- separate table while preserving value type semantics for all
- properties:
-
- <class name="Person"
- table="PERSON">
-
- <id name="id" column="PERSON_ID">...</id>
-
- <join table="ADDRESS">
- <key column="ADDRESS_ID"/>
- <property name="address"/>
- <property name="zip"/>
- <property name="country"/>
- </join>
- ...
-
- This feature is often only useful for legacy data models. We
- recommend fewer tables than classes and a fine-grained domain model.
- However, it is useful for switching between inheritance mapping
- strategies in a single hierarchy, as explained later.
-
-
-
Optimistic locking properties (optional)
@@ -4182,6 +3046,1012 @@ public long getObjectVolume()
+
+ Embedded objects (aka components)
+
+ Embeddable objects (or components) are objects whose properties
+ are mapped to the same table as the owning entity's table. Components
+ can, in turn, declare their own properties, components or
+ collections
+
+ It is possible to declare an embedded component inside an entity
+ and even override its column mapping. Component classes have to be
+ annotated at the class level with the @Embeddable
+ annotation. It is possible to override the column mapping of an embedded
+ object for a particular entity using the @Embedded
+ and @AttributeOverride annotation in the associated
+ property:
+
+ @Entity
+public class Person implements Serializable {
+
+ // Persistent component using defaults
+ Address homeAddress;
+
+ @Embedded
+ @AttributeOverrides( {
+ @AttributeOverride(name="iso2", column = @Column(name="bornIso2") ),
+ @AttributeOverride(name="name", column = @Column(name="bornCountryName") )
+ } )
+ Country bornIn;
+ ...
+}
+
+ @Embeddable
+public class Address implements Serializable {
+ String city;
+ Country nationality; //no overriding here
+}
+
+ @Embeddable
+public class Country implements Serializable {
+ private String iso2;
+ @Column(name="countryName") private String name;
+
+ public String getIso2() { return iso2; }
+ public void setIso2(String iso2) { this.iso2 = iso2; }
+
+
+ public String getName() { return name; }
+ public void setName(String name) { this.name = name; }
+ ...
+}
+
+ An embeddable object inherits the access type of its owning entity
+ (note that you can override that using the @Access
+ annotation).
+
+ The Person entity has two component properties,
+ homeAddress and bornIn.
+ homeAddress property has not been annotated, but
+ Hibernate will guess that it is a persistent component by looking for
+ the @Embeddable annotation in the Address class. We
+ also override the mapping of a column name (to
+ bornCountryName) with the
+ @Embedded and @AttributeOverride
+ annotations for each mapped attribute of
+ Country. As you can see, Country
+ is also a nested component of Address,
+ again using auto-detection by Hibernate and JPA defaults. Overriding
+ columns of embedded objects of embedded objects is through dotted
+ expressions.
+
+ @Embedded
+ @AttributeOverrides( {
+ @AttributeOverride(name="city", column = @Column(name="fld_city") ),
+ @AttributeOverride(name="nationality.iso2", column = @Column(name="nat_Iso2") ),
+ @AttributeOverride(name="nationality.name", column = @Column(name="nat_CountryName") )
+ //nationality columns in homeAddress are overridden
+ } )
+ Address homeAddress;
+
+ Hibernate Annotations supports something that is not explicitly
+ supported by the JPA specification. You can annotate a embedded object
+ with the @MappedSuperclass annotation to make the
+ superclass properties persistent (see
+ @MappedSuperclass for more informations).
+
+ You can also use association annotations in an embeddable object
+ (ie @OneToOne, @ManyToOne,
+ @OneToMany or @ManyToMany). To
+ override the association columns you can use
+ @AssociationOverride.
+
+ If you want to have the same embeddable object type twice in the
+ same entity, the column name defaulting will not work as several
+ embedded objects would share the same set of columns. In plain JPA, you
+ need to override at least one set of columns. Hibernate, however, allows
+ you to enhance the default naming mechanism through the
+ NamingStrategy interface. You can write a
+ strategy that prevent name clashing in such a situation.
+ DefaultComponentSafeNamingStrategy is an example
+ of this.
+
+ If a property of the embedded object points back to the owning
+ entity, annotate it with the @Parent annotation.
+ Hibernate will make sure this property is properly loaded with the
+ entity reference.
+
+ In XML, use the <component>
+ element.
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ <component
+ name="propertyName"
+ class="className"
+ insert="true|false"
+ update="true|false"
+ access="field|property|ClassName"
+ lazy="true|false"
+ optimistic-lock="true|false"
+ unique="true|false"
+ node="element-name|."
+>
+
+ <property ...../>
+ <many-to-one .... />
+ ........
+</component>
+
+
+
+ name: the name of the property.
+
+
+
+ class (optional - defaults to the
+ property type determined by reflection): the name of the component
+ (child) class.
+
+
+
+ insert: do the mapped columns appear in
+ SQL INSERTs?
+
+
+
+ update: do the mapped columns appear in
+ SQL UPDATEs?
+
+
+
+ access (optional - defaults to
+ property): the strategy Hibernate uses for
+ accessing the property value.
+
+
+
+ lazy (optional - defaults to
+ false): specifies that this component should be
+ fetched lazily when the instance variable is first accessed. It
+ requires build-time bytecode instrumentation.
+
+
+
+ optimistic-lock (optional - defaults to
+ true): specifies that updates to this component
+ either do or do not require acquisition of the optimistic lock. It
+ determines if a version increment should occur when this property
+ is dirty.
+
+
+
+ unique (optional - defaults to
+ false): specifies that a unique constraint
+ exists upon all mapped columns of the component.
+
+
+
+
+ The child <property> tags map properties
+ of the child class to table columns.
+
+ The <component> element allows a
+ <parent> subelement that maps a property of the
+ component class as a reference back to the containing entity.
+
+ The <dynamic-component> element allows a
+ Map to be mapped as a component, where the property
+ names refer to keys of the map. See for more information. This feature is
+ not supported in annotations.
+
+
+
+ Inheritance strategy
+
+ Java is a language supporting polymorphism: a class can inherit
+ from another. Several strategies are possible to persist a class
+ hierarchy:
+
+
+
+ Single table per class hierarchy strategy: a single table
+ hosts all the instances of a class hierarchy
+
+
+
+ Joined subclass strategy: one table per class and subclass is
+ present and each table persist the properties specific to a given
+ subclass. The state of the entity is then stored in its
+ corresponding class table and all its superclasses
+
+
+
+ Table per class strategy: one table per concrete class and
+ subclass is present and each table persist the properties of the
+ class and its superclasses. The state of the entity is then stored
+ entirely in the dedicated table for its class.
+
+
+
+
+ Single table per class hierarchy strategy
+
+ With this approach the properties of all the subclasses in a
+ given mapped class hierarchy are stored in a single table.
+
+ Each subclass declares its own persistent properties and
+ subclasses. Version and id properties are assumed to be inherited from
+ the root class. Each subclass in a hierarchy must define a unique
+ discriminator value. If this is not specified, the fully qualified
+ Java class name is used.
+
+ @Entity
+@Inheritance(strategy=InheritanceType.SINGLE_TABLE)
+@DiscriminatorColumn(
+ name="planetype",
+ discriminatorType=DiscriminatorType.STRING
+)
+@DiscriminatorValue("Plane")
+public class Plane { ... }
+
+@Entity
+@DiscriminatorValue("A320")
+public class A320 extends Plane { ... }
+
+ In hbm.xml, for the table-per-class-hierarchy mapping strategy,
+ the <subclass> declaration is used. For
+ example:
+
+
+
+
+
+
+
+
+
+
+
+
+ <subclass
+ name="ClassName"
+ discriminator-value="discriminator_value"
+ proxy="ProxyInterface"
+ lazy="true|false"
+ dynamic-update="true|false"
+ dynamic-insert="true|false"
+ entity-name="EntityName"
+ node="element-name"
+ extends="SuperclassName">
+
+ <property .... />
+ .....
+</subclass>
+
+
+
+ name: the fully qualified class name of
+ the subclass.
+
+
+
+ discriminator-value (optional -
+ defaults to the class name): a value that distinguishes
+ individual subclasses.
+
+
+
+ proxy (optional): specifies a class or
+ interface used for lazy initializing proxies.
+
+
+
+ lazy (optional - defaults to
+ true): setting
+ lazy="false" disables the use of lazy
+ fetching.
+
+
+
+
+ For information about inheritance mappings see .
+
+
+ Discriminator
+
+ Discriminators are required for polymorphic persistence using
+ the table-per-class-hierarchy mapping strategy. It declares a
+ discriminator column of the table. The discriminator column contains
+ marker values that tell the persistence layer what subclass to
+ instantiate for a particular row. A restricted set of types can be
+ used: string, character,
+ integer, byte,
+ short, boolean,
+ yes_no, true_false.
+
+ Use the @DiscriminatorColumn to define
+ the discriminator column as well as the discriminator type.
+ Alternatively, you can also use
+ @DiscriminatorFormula to express in SQL what
+ would be in a virtual discriminator column. This is particularly
+ handy when the discriminator value can be extracted from one or more
+ columns of the table. Both
+ @DiscriminatorColumn and
+ @DiscriminatorFormula are to be set on the
+ root entity (once per persisted hierarchy).
+
+ Finally, use @DiscriminatorValue on
+ each class of the hierarchy to specify the value stored in the
+ discriminator column for a given entity. If you do not set
+ @DiscriminatorValue on a class, the fully
+ qualified class name is used.
+
+ @Entity
+@Inheritance(strategy=InheritanceType.SINGLE_TABLE)
+@DiscriminatorColumn(
+ name="planetype",
+ discriminatorType=DiscriminatorType.STRING
+)
+@DiscriminatorValue("Plane")
+public class Plane { ... }
+
+@Entity
+@DiscriminatorValue("A320")
+public class A320 extends Plane { ... }
+
+ In hbm.xml, the <discriminator>
+ element is used to define the discriminator column or
+ formula:
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ <discriminator
+ column="discriminator_column"
+ type="discriminator_type"
+ force="true|false"
+ insert="true|false"
+ formula="arbitrary sql expression"
+/>
+
+
+
+ column (optional - defaults to
+ class): the name of the discriminator
+ column.
+
+
+
+ type (optional - defaults to
+ string): a name that indicates the
+ Hibernate type
+
+
+
+ force (optional - defaults to
+ false): "forces" Hibernate to specify the
+ allowed discriminator values, even when retrieving all
+ instances of the root class.
+
+
+
+ insert (optional - defaults to
+ true): set this to false
+ if your discriminator column is also part of a mapped
+ composite identifier. It tells Hibernate not to include the
+ column in SQL INSERTs.
+
+
+
+ formula (optional): an arbitrary SQL
+ expression that is executed when a type has to be evaluated.
+ It allows content-based discrimination.
+
+
+
+
+ Actual values of the discriminator column are specified by the
+ discriminator-value attribute of the
+ <class> and
+ <subclass> elements.
+
+ The force attribute is only useful if the
+ table contains rows with "extra" discriminator values that are not
+ mapped to a persistent class. This will not usually be the
+ case.
+
+ The formula attribute allows you to declare
+ an arbitrary SQL expression that will be used to evaluate the type
+ of a row. For example:
+
+ <discriminator
+ formula="case when CLASS_TYPE in ('a', 'b', 'c') then 0 else 1 end"
+ type="integer"/>
+
+
+
+
+ Joined subclass strategy
+
+ Each subclass can also be mapped to its own table. This is
+ called the table-per-subclass mapping strategy. An inherited state is
+ retrieved by joining with the table of the superclass. A discriminator
+ column is not required for this mapping strategy. Each subclass must,
+ however, declare a table column holding the object identifier. The
+ primary key of this table is also a foreign key to the superclass
+ table and described by the
+ @PrimaryKeyJoinColumns or the
+ <key> element.
+
+ @Entity @Table(name="CATS")
+@Inheritance(strategy=InheritanceType.JOINED)
+public class Cat implements Serializable {
+ @Id @GeneratedValue(generator="cat-uuid")
+ @GenericGenerator(name="cat-uuid", strategy="uuid")
+ String getId() { return id; }
+
+ ...
+}
+
+@Entity @Table(name="DOMESTIC_CATS")
+@PrimaryKeyJoinColumn(name="CAT")
+public class DomesticCat extends Cat {
+ public String getName() { return name; }
+}
+
+
+ The table name still defaults to the non qualified class name.
+ Also if @PrimaryKeyJoinColumn is not set, the
+ primary key / foreign key columns are assumed to have the same names
+ as the primary key columns of the primary table of the
+ superclass.
+
+
+ In hbm.xml, use the <joined-subclass>
+ element. For example:
+
+
+
+
+
+
+
+
+
+
+
+
+ <joined-subclass
+ name="ClassName"
+ table="tablename"
+ proxy="ProxyInterface"
+ lazy="true|false"
+ dynamic-update="true|false"
+ dynamic-insert="true|false"
+ schema="schema"
+ catalog="catalog"
+ extends="SuperclassName"
+ persister="ClassName"
+ subselect="SQL expression"
+ entity-name="EntityName"
+ node="element-name">
+
+ <key .... >
+
+ <property .... />
+ .....
+</joined-subclass>
+
+
+
+ name: the fully qualified class name of
+ the subclass.
+
+
+
+ table: the name of the subclass
+ table.
+
+
+
+ proxy (optional): specifies a class or
+ interface to use for lazy initializing proxies.
+
+
+
+ lazy (optional, defaults to
+ true): setting
+ lazy="false" disables the use of lazy
+ fetching.
+
+
+
+
+ Use the <key> element to declare the
+ primary key / foreign key column. The mapping at the start of the
+ chapter would then be re-written as:
+
+ <?xml version="1.0"?>
+<!DOCTYPE hibernate-mapping PUBLIC
+ "-//Hibernate/Hibernate Mapping DTD//EN"
+ "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
+
+<hibernate-mapping package="eg">
+
+ <class name="Cat" table="CATS">
+ <id name="id" column="uid" type="long">
+ <generator class="hilo"/>
+ </id>
+ <property name="birthdate" type="date"/>
+ <property name="color" not-null="true"/>
+ <property name="sex" not-null="true"/>
+ <property name="weight"/>
+ <many-to-one name="mate"/>
+ <set name="kittens">
+ <key column="MOTHER"/>
+ <one-to-many class="Cat"/>
+ </set>
+ <joined-subclass name="DomesticCat" table="DOMESTIC_CATS">
+ <key column="CAT"/>
+ <property name="name" type="string"/>
+ </joined-subclass>
+ </class>
+
+ <class name="eg.Dog">
+ <!-- mapping for Dog could go here -->
+ </class>
+
+</hibernate-mapping>
+
+ For information about inheritance mappings see .
+
+
+
+ Table per class strategy
+
+ A third option is to map only the concrete classes of an
+ inheritance hierarchy to tables. This is called the
+ table-per-concrete-class strategy. Each table defines all persistent
+ states of the class, including the inherited state. In Hibernate, it
+ is not necessary to explicitly map such inheritance hierarchies. You
+ can map each class as a separate entity root. However, if you wish use
+ polymorphic associations (e.g. an association to the superclass of
+ your hierarchy), you need to use the union subclass mapping.
+
+ @Entity
+@Inheritance(strategy = InheritanceType.TABLE_PER_CLASS)
+public class Flight implements Serializable { ... }
+
+ Or in hbm.xml:
+
+
+
+
+
+
+
+
+
+
+
+
+ <union-subclass
+ name="ClassName"
+ table="tablename"
+ proxy="ProxyInterface"
+ lazy="true|false"
+ dynamic-update="true|false"
+ dynamic-insert="true|false"
+ schema="schema"
+ catalog="catalog"
+ extends="SuperclassName"
+ abstract="true|false"
+ persister="ClassName"
+ subselect="SQL expression"
+ entity-name="EntityName"
+ node="element-name">
+
+ <property .... />
+ .....
+</union-subclass>
+
+
+
+ name: the fully qualified class name of
+ the subclass.
+
+
+
+ table: the name of the subclass
+ table.
+
+
+
+ proxy (optional): specifies a class or
+ interface to use for lazy initializing proxies.
+
+
+
+ lazy (optional, defaults to
+ true): setting
+ lazy="false" disables the use of lazy
+ fetching.
+
+
+
+
+ No discriminator column or key column is required for this
+ mapping strategy.
+
+ For information about inheritance mappings see .
+
+
+
+ Inherit properties from superclasses
+
+ This is sometimes useful to share common properties through a
+ technical or a business superclass without including it as a regular
+ mapped entity (ie no specific table for this entity). For that purpose
+ you can map them as @MappedSuperclass.
+
+ @MappedSuperclass
+public class BaseEntity {
+ @Basic
+ @Temporal(TemporalType.TIMESTAMP)
+ public Date getLastUpdate() { ... }
+ public String getLastUpdater() { ... }
+ ...
+}
+
+@Entity class Order extends BaseEntity {
+ @Id public Integer getId() { ... }
+ ...
+}
+
+ In database, this hierarchy will be represented as an
+ Order table having the id,
+ lastUpdate and lastUpdater
+ columns. The embedded superclass property mappings are copied into
+ their entity subclasses. Remember that the embeddable superclass is
+ not the root of the hierarchy though.
+
+
+ Properties from superclasses not mapped as
+ @MappedSuperclass are ignored.
+
+
+
+ The default access type (field or methods) is used, unless you
+ use the @Access annotation.
+
+
+
+ The same notion can be applied to
+ @Embeddable objects to persist properties from
+ their superclasses. You also need to use
+ @MappedSuperclass to do that (this should not be
+ considered as a standard EJB3 feature though)
+
+
+
+ It is allowed to mark a class as
+ @MappedSuperclass in the middle of the mapped
+ inheritance hierarchy.
+
+
+
+ Any class in the hierarchy non annotated with
+ @MappedSuperclass nor @Entity
+ will be ignored.
+
+
+ You can override columns defined in entity superclasses at the
+ root entity level using the @AttributeOverride
+ annotation.
+
+ @MappedSuperclass
+public class FlyingObject implements Serializable {
+
+ public int getAltitude() {
+ return altitude;
+ }
+
+ @Transient
+ public int getMetricAltitude() {
+ return metricAltitude;
+ }
+
+ @ManyToOne
+ public PropulsionType getPropulsion() {
+ return metricAltitude;
+ }
+ ...
+}
+
+@Entity
+@AttributeOverride( name="altitude", column = @Column(name="fld_altitude") )
+@AssociationOverride(
+ name="propulsion",
+ joinColumns = @JoinColumn(name="fld_propulsion_fk")
+)
+public class Plane extends FlyingObject {
+ ...
+}
+
+ The altitude property will be persisted in an
+ fld_altitude column of table
+ Plane and the propulsion association will be
+ materialized in a fld_propulsion_fk foreign key
+ column.
+
+ You can define @AttributeOverride(s) and
+ @AssociationOverride(s) on
+ @Entity classes,
+ @MappedSuperclass classes and properties pointing
+ to an @Embeddable object.
+
+ In hbm.xml, simply map the properties of the superclass in the
+ <class> element of the entity that needs to
+ inherit them.
+
+
+
+ Mapping one entity to several tables
+
+ While not recommended for a fresh schema, some legacy databases
+ force your to map a single entity on several tables.
+
+ Using the @SecondaryTable or
+ @SecondaryTables class level annotations. To
+ express that a column is in a particular table, use the
+ table parameter of @Column or
+ @JoinColumn.
+
+ @Entity
+@Table(name="MainCat")
+@SecondaryTables({
+ @SecondaryTable(name="Cat1", pkJoinColumns={
+ @PrimaryKeyJoinColumn(name="cat_id", referencedColumnName="id")
+ ),
+ @SecondaryTable(name="Cat2", uniqueConstraints={@UniqueConstraint(columnNames={"storyPart2"})})
+})
+public class Cat implements Serializable {
+
+ private Integer id;
+ private String name;
+ private String storyPart1;
+ private String storyPart2;
+
+ @Id @GeneratedValue
+ public Integer getId() {
+ return id;
+ }
+
+ public String getName() {
+ return name;
+ }
+
+ @Column(table="Cat1")
+ public String getStoryPart1() {
+ return storyPart1;
+ }
+
+ @Column(table="Cat2")
+ public String getStoryPart2() {
+ return storyPart2;
+ }
+}
+
+ In this example, name will be in
+ MainCat. storyPart1 will be in
+ Cat1 and storyPart2 will be in
+ Cat2. Cat1 will be joined to
+ MainCat using the cat_id as a
+ foreign key, and Cat2 using id
+ (ie the same column name, the MainCat id column
+ has). Plus a unique constraint on storyPart2 has
+ been set.
+
+ There is also additional tuning accessible via the
+ @org.hibernate.annotations.Table
+ annotation:
+
+
+
+ fetch: If set to JOIN, the default,
+ Hibernate will use an inner join to retrieve a secondary table
+ defined by a class or its superclasses and an outer join for a
+ secondary table defined by a subclass. If set to
+ SELECT then Hibernate will use a sequential
+ select for a secondary table defined on a subclass, which will be
+ issued only if a row turns out to represent an instance of the
+ subclass. Inner joins will still be used to retrieve a secondary
+ defined by the class and its superclasses.
+
+
+
+ inverse: If true, Hibernate will not try
+ to insert or update the properties defined by this join. Default
+ to false.
+
+
+
+ optional: If enabled (the default),
+ Hibernate will insert a row only if the properties defined by this
+ join are non-null and will always use an outer join to retrieve
+ the properties.
+
+
+
+ foreignKey: defines the Foreign Key name
+ of a secondary table pointing back to the primary table.
+
+
+
+ Make sure to use the secondary table name in the
+ appliesto property
+
+ @Entity
+@Table(name="MainCat")
+@SecondaryTable(name="Cat1")
+@org.hibernate.annotations.Table(
+ appliesTo="Cat1",
+ fetch=FetchMode.SELECT,
+ optional=true)
+public class Cat implements Serializable {
+
+ private Integer id;
+ private String name;
+ private String storyPart1;
+ private String storyPart2;
+
+ @Id @GeneratedValue
+ public Integer getId() {
+ return id;
+ }
+
+ public String getName() {
+ return name;
+ }
+
+ @Column(table="Cat1")
+ public String getStoryPart1() {
+ return storyPart1;
+ }
+
+ @Column(table="Cat2")
+ public String getStoryPart2() {
+ return storyPart2;
+ }
+}
+
+ In hbm.xml, use the <join>
+ element.
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ <join
+ table="tablename"
+ schema="owner"
+ catalog="catalog"
+ fetch="join|select"
+ inverse="true|false"
+ optional="true|false">
+
+ <key ... />
+
+ <property ... />
+ ...
+</join>
+
+
+
+ table: the name of the joined
+ table.
+
+
+
+ schema (optional): overrides the schema
+ name specified by the root
+ <hibernate-mapping> element.
+
+
+
+ catalog (optional): overrides the
+ catalog name specified by the root
+ <hibernate-mapping> element.
+
+
+
+ fetch (optional - defaults to
+ join): if set to join, the
+ default, Hibernate will use an inner join to retrieve a
+ <join> defined by a class or its
+ superclasses. It will use an outer join for a
+ <join> defined by a subclass. If set to
+ select then Hibernate will use a sequential
+ select for a <join> defined on a
+ subclass. This will be issued only if a row represents an
+ instance of the subclass. Inner joins will still be used to
+ retrieve a <join> defined by the class
+ and its superclasses.
+
+
+
+ inverse (optional - defaults to
+ false): if enabled, Hibernate will not insert
+ or update the properties defined by this join.
+
+
+
+ optional (optional - defaults to
+ false): if enabled, Hibernate will insert a
+ row only if the properties defined by this join are non-null. It
+ will always use an outer join to retrieve the properties.
+
+
+
+
+ For example, address information for a person can be mapped to a
+ separate table while preserving value type semantics for all
+ properties:
+
+ <class name="Person"
+ table="PERSON">
+
+ <id name="id" column="PERSON_ID">...</id>
+
+ <join table="ADDRESS">
+ <key column="ADDRESS_ID"/>
+ <property name="address"/>
+ <property name="zip"/>
+ <property name="country"/>
+ </join>
+ ...
+
+ This feature is often only useful for legacy data models. We
+ recommend fewer tables than classes and a fine-grained domain model.
+ However, it is useful for switching between inheritance mapping
+ strategies in a single hierarchy, as explained later.
+
+
+
Mapping one to one and one to many associations
@@ -4900,339 +4770,6 @@ List results = s.createCriteria( Citizen.class )
-
- Embedded objects (aka components)
-
- Embeddable objects (or components) are objects whose properties
- are mapped to the same table as the owning entity's table. Components
- can, in turn, declare their own properties, components or
- collections
-
- It is possible to declare an embedded component inside an entity
- and even override its column mapping. Component classes have to be
- annotated at the class level with the @Embeddable
- annotation. It is possible to override the column mapping of an embedded
- object for a particular entity using the @Embedded
- and @AttributeOverride annotation in the associated
- property:
-
- @Entity
-public class Person implements Serializable {
-
- // Persistent component using defaults
- Address homeAddress;
-
- @Embedded
- @AttributeOverrides( {
- @AttributeOverride(name="iso2", column = @Column(name="bornIso2") ),
- @AttributeOverride(name="name", column = @Column(name="bornCountryName") )
- } )
- Country bornIn;
- ...
-}
-
- @Embeddable
-public class Address implements Serializable {
- String city;
- Country nationality; //no overriding here
-}
-
- @Embeddable
-public class Country implements Serializable {
- private String iso2;
- @Column(name="countryName") private String name;
-
- public String getIso2() { return iso2; }
- public void setIso2(String iso2) { this.iso2 = iso2; }
-
-
- public String getName() { return name; }
- public void setName(String name) { this.name = name; }
- ...
-}
-
- An embeddable object inherits the access type of its owning entity
- (note that you can override that using the @Access
- annotation).
-
- The Person entity has two component properties,
- homeAddress and bornIn.
- homeAddress property has not been annotated, but
- Hibernate will guess that it is a persistent component by looking for
- the @Embeddable annotation in the Address class. We
- also override the mapping of a column name (to
- bornCountryName) with the
- @Embedded and @AttributeOverride
- annotations for each mapped attribute of
- Country. As you can see, Country
- is also a nested component of Address,
- again using auto-detection by Hibernate and JPA defaults. Overriding
- columns of embedded objects of embedded objects is through dotted
- expressions.
-
- @Embedded
- @AttributeOverrides( {
- @AttributeOverride(name="city", column = @Column(name="fld_city") ),
- @AttributeOverride(name="nationality.iso2", column = @Column(name="nat_Iso2") ),
- @AttributeOverride(name="nationality.name", column = @Column(name="nat_CountryName") )
- //nationality columns in homeAddress are overridden
- } )
- Address homeAddress;
-
- Hibernate Annotations supports something that is not explicitly
- supported by the JPA specification. You can annotate a embedded object
- with the @MappedSuperclass annotation to make the
- superclass properties persistent (see
- @MappedSuperclass for more informations).
-
- You can also use association annotations in an embeddable object
- (ie @OneToOne, @ManyToOne,
- @OneToMany or @ManyToMany). To
- override the association columns you can use
- @AssociationOverride.
-
- If you want to have the same embeddable object type twice in the
- same entity, the column name defaulting will not work as several
- embedded objects would share the same set of columns. In plain JPA, you
- need to override at least one set of columns. Hibernate, however, allows
- you to enhance the default naming mechanism through the
- NamingStrategy interface. You can write a
- strategy that prevent name clashing in such a situation.
- DefaultComponentSafeNamingStrategy is an example
- of this.
-
- If a property of the embedded object points back to the owning
- entity, annotate it with the @Parent annotation.
- Hibernate will make sure this property is properly loaded with the
- entity reference.
-
- In XML, use the <component>
- element.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- <component
- name="propertyName"
- class="className"
- insert="true|false"
- update="true|false"
- access="field|property|ClassName"
- lazy="true|false"
- optimistic-lock="true|false"
- unique="true|false"
- node="element-name|."
->
-
- <property ...../>
- <many-to-one .... />
- ........
-</component>
-
-
-
- name: the name of the property.
-
-
-
- class (optional - defaults to the
- property type determined by reflection): the name of the component
- (child) class.
-
-
-
- insert: do the mapped columns appear in
- SQL INSERTs?
-
-
-
- update: do the mapped columns appear in
- SQL UPDATEs?
-
-
-
- access (optional - defaults to
- property): the strategy Hibernate uses for
- accessing the property value.
-
-
-
- lazy (optional - defaults to
- false): specifies that this component should be
- fetched lazily when the instance variable is first accessed. It
- requires build-time bytecode instrumentation.
-
-
-
- optimistic-lock (optional - defaults to
- true): specifies that updates to this component
- either do or do not require acquisition of the optimistic lock. It
- determines if a version increment should occur when this property
- is dirty.
-
-
-
- unique (optional - defaults to
- false): specifies that a unique constraint
- exists upon all mapped columns of the component.
-
-
-
-
- The child <property> tags map properties
- of the child class to table columns.
-
- The <component> element allows a
- <parent> subelement that maps a property of the
- component class as a reference back to the containing entity.
-
- The <dynamic-component> element allows a
- Map to be mapped as a component, where the property
- names refer to keys of the map. See for more information. This feature is
- not supported in annotations.
-
-
-
- Properties
-
- The <properties> element allows the
- definition of a named, logical grouping of the properties of a class.
- The most important use of the construct is that it allows a combination
- of properties to be the target of a property-ref. It
- is also a convenient way to define a multi-column unique constraint. For
- example:
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- <properties
- name="logicalName"
- insert="true|false"
- update="true|false"
- optimistic-lock="true|false"
- unique="true|false"
->
-
- <property ...../>
- <many-to-one .... />
- ........
-</properties>
-
-
-
- name: the logical name of the grouping.
- It is not an actual property name.
-
-
-
- insert: do the mapped columns appear in
- SQL INSERTs?
-
-
-
- update: do the mapped columns appear in
- SQL UPDATEs?
-
-
-
- optimistic-lock (optional - defaults to
- true): specifies that updates to these
- properties either do or do not require acquisition of the
- optimistic lock. It determines if a version increment should occur
- when these properties are dirty.
-
-
-
- unique (optional - defaults to
- false): specifies that a unique constraint
- exists upon all mapped columns of the component.
-
-
-
-
- For example, if we have the following
- <properties> mapping:
-
- <class name="Person">
- <id name="personNumber"/>
-
- ...
- <properties name="name"
- unique="true" update="false">
- <property name="firstName"/>
- <property name="initial"/>
- <property name="lastName"/>
- </properties>
-</class>
-
- You might have some legacy data association that refers to this
- unique key of the Person table, instead of to the
- primary key:
-
- <many-to-one name="owner"
- class="Person" property-ref="name">
- <column name="firstName"/>
- <column name="initial"/>
- <column name="lastName"/>
-</many-to-one>
-
-
- When using annotations as a mapping strategy, such construct is
- not necessary as the binding between a column and its related column
- on the associated table is done directly
-
- @Entity
-class Person {
- @Id Integer personNumber;
- String firstName;
- @Column(name="I")
- String initial;
- String lastName;
-}
-
-@Entity
-class Home {
- @ManyToOne
- @JoinColumns({
- @JoinColumn(name="first_name", referencedColumnName="firstName"),
- @JoinColumn(name="init", referencedColumnName="I"),
- @JoinColumn(name="last_name", referencedColumnName="lastName"),
- })
- Person owner
-}
-
-
- The use of this outside the context of mapping legacy data is not
- recommended.
-
-
Any
@@ -5373,6 +4910,469 @@ package org.hibernate.test.annotations.any;
+
+
+ Properties
+
+ The <properties> element allows the
+ definition of a named, logical grouping of the properties of a class.
+ The most important use of the construct is that it allows a combination
+ of properties to be the target of a property-ref. It
+ is also a convenient way to define a multi-column unique constraint. For
+ example:
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ <properties
+ name="logicalName"
+ insert="true|false"
+ update="true|false"
+ optimistic-lock="true|false"
+ unique="true|false"
+>
+
+ <property ...../>
+ <many-to-one .... />
+ ........
+</properties>
+
+
+
+ name: the logical name of the grouping.
+ It is not an actual property name.
+
+
+
+ insert: do the mapped columns appear in
+ SQL INSERTs?
+
+
+
+ update: do the mapped columns appear in
+ SQL UPDATEs?
+
+
+
+ optimistic-lock (optional - defaults to
+ true): specifies that updates to these
+ properties either do or do not require acquisition of the
+ optimistic lock. It determines if a version increment should occur
+ when these properties are dirty.
+
+
+
+ unique (optional - defaults to
+ false): specifies that a unique constraint
+ exists upon all mapped columns of the component.
+
+
+
+
+ For example, if we have the following
+ <properties> mapping:
+
+ <class name="Person">
+ <id name="personNumber"/>
+
+ ...
+ <properties name="name"
+ unique="true" update="false">
+ <property name="firstName"/>
+ <property name="initial"/>
+ <property name="lastName"/>
+ </properties>
+</class>
+
+ You might have some legacy data association that refers to this
+ unique key of the Person table, instead of to the
+ primary key:
+
+ <many-to-one name="owner"
+ class="Person" property-ref="name">
+ <column name="firstName"/>
+ <column name="initial"/>
+ <column name="lastName"/>
+</many-to-one>
+
+
+ When using annotations as a mapping strategy, such construct is
+ not necessary as the binding between a column and its related column
+ on the associated table is done directly
+
+ @Entity
+class Person {
+ @Id Integer personNumber;
+ String firstName;
+ @Column(name="I")
+ String initial;
+ String lastName;
+}
+
+@Entity
+class Home {
+ @ManyToOne
+ @JoinColumns({
+ @JoinColumn(name="first_name", referencedColumnName="firstName"),
+ @JoinColumn(name="init", referencedColumnName="I"),
+ @JoinColumn(name="last_name", referencedColumnName="lastName"),
+ })
+ Person owner
+}
+
+
+ The use of this outside the context of mapping legacy data is not
+ recommended.
+
+
+
+ Some hbm.xml specificities
+
+ The hbm.xml structure has some specificities naturally not present
+ when using annotations, let's describe them briefly.
+
+
+ Doctype
+
+ All XML mappings should declare the doctype shown. The actual
+ DTD can be found at the URL above, in the directory
+ hibernate-x.x.x/src/org/hibernate , or in
+ hibernate3.jar. Hibernate will always look for the
+ DTD in its classpath first. If you experience lookups of the DTD using
+ an Internet connection, check the DTD declaration against the contents
+ of your classpath.
+
+
+ EntityResolver
+
+ Hibernate will first attempt to resolve DTDs in its classpath.
+ It does this is by registering a custom
+ org.xml.sax.EntityResolver implementation with
+ the SAXReader it uses to read in the xml files. This custom
+ EntityResolver recognizes two different systemId
+ namespaces:
+
+
+
+ a hibernate namespace is recognized
+ whenever the resolver encounters a systemId starting with
+ http://hibernate.sourceforge.net/. The
+ resolver attempts to resolve these entities via the classloader
+ which loaded the Hibernate classes.
+
+
+
+ a user namespace is recognized whenever
+ the resolver encounters a systemId using a
+ classpath:// URL protocol. The resolver will
+ attempt to resolve these entities via (1) the current thread
+ context classloader and (2) the classloader which loaded the
+ Hibernate classes.
+
+
+
+ The following is an example of utilizing user
+ namespacing:
+
+
+
+
+
+ Where types.xml is a resource in the
+ your.domain package and contains a custom typedef.
+
+
+
+
+ Hibernate-mapping
+
+ This element has several optional attributes. The
+ schema and catalog attributes
+ specify that tables referred to in this mapping belong to the named
+ schema and/or catalog. If they are specified, tablenames will be
+ qualified by the given schema and catalog names. If they are missing,
+ tablenames will be unqualified. The default-cascade
+ attribute specifies what cascade style should be assumed for
+ properties and collections that do not specify a
+ cascade attribute. By default, the
+ auto-import attribute allows you to use unqualified
+ class names in the query language.
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ <hibernate-mapping
+ schema="schemaName"
+ catalog="catalogName"
+ default-cascade="cascade_style"
+ default-access="field|property|ClassName"
+ default-lazy="true|false"
+ auto-import="true|false"
+ package="package.name"
+ />
+
+
+
+ schema (optional): the name of a
+ database schema.
+
+
+
+ catalog (optional): the name of a
+ database catalog.
+
+
+
+ default-cascade (optional - defaults to
+ none): a default cascade style.
+
+
+
+ default-access (optional - defaults to
+ property): the strategy Hibernate should use
+ for accessing all properties. It can be a custom implementation
+ of PropertyAccessor.
+
+
+
+ default-lazy (optional - defaults to
+ true): the default value for unspecified
+ lazy attributes of class and collection
+ mappings.
+
+
+
+ auto-import (optional - defaults to
+ true): specifies whether we can use
+ unqualified class names of classes in this mapping in the query
+ language.
+
+
+
+ package (optional): specifies a package
+ prefix to use for unqualified class names in the mapping
+ document.
+
+
+
+
+ If you have two persistent classes with the same unqualified
+ name, you should set auto-import="false". An
+ exception will result if you attempt to assign two classes to the same
+ "imported" name.
+
+ The hibernate-mapping element allows you to
+ nest several persistent <class> mappings, as
+ shown above. It is, however, good practice (and expected by some
+ tools) to map only a single persistent class, or a single class
+ hierarchy, in one mapping file and name it after the persistent
+ superclass. For example, Cat.hbm.xml,
+ Dog.hbm.xml, or if using inheritance,
+ Animal.hbm.xml.
+
+
+
+ Key
+
+ The <key> element is featured a few
+ times within this guide. It appears anywhere the parent mapping
+ element defines a join to a new table that references the primary key
+ of the original table. It also defines the foreign key in the joined
+ table:
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ <key
+ column="columnname"
+ on-delete="noaction|cascade"
+ property-ref="propertyName"
+ not-null="true|false"
+ update="true|false"
+ unique="true|false"
+/>
+
+
+
+ column (optional): the name of the
+ foreign key column. This can also be specified by nested
+ <column> element(s).
+
+
+
+ on-delete (optional - defaults to
+ noaction): specifies whether the foreign key
+ constraint has database-level cascade delete enabled.
+
+
+
+ property-ref (optional): specifies that
+ the foreign key refers to columns that are not the primary key
+ of the original table. It is provided for legacy data.
+
+
+
+ not-null (optional): specifies that the
+ foreign key columns are not nullable. This is implied whenever
+ the foreign key is also part of the primary key.
+
+
+
+ update (optional): specifies that the
+ foreign key should never be updated. This is implied whenever
+ the foreign key is also part of the primary key.
+
+
+
+ unique (optional): specifies that the
+ foreign key should have a unique constraint. This is implied
+ whenever the foreign key is also the primary key.
+
+
+
+
+ For systems where delete performance is important, we recommend
+ that all keys should be defined
+ on-delete="cascade". Hibernate uses a
+ database-level ON CASCADE DELETE constraint,
+ instead of many individual DELETE statements. Be
+ aware that this feature bypasses Hibernate's usual optimistic locking
+ strategy for versioned data.
+
+ The not-null and update
+ attributes are useful when mapping a unidirectional one-to-many
+ association. If you map a unidirectional one-to-many association to a
+ non-nullable foreign key, you must declare the
+ key column using <key
+ not-null="true">.
+
+
+
+ Import
+
+ If your application has two persistent classes with the same
+ name, and you do not want to specify the fully qualified package name
+ in Hibernate queries, classes can be "imported" explicitly, rather
+ than relying upon auto-import="true". You can also
+ import classes and interfaces that are not explicitly mapped:
+
+ <import class="java.lang.Object" rename="Universe"/>
+
+
+
+
+
+
+
+
+ <import
+ class="ClassName"
+ rename="ShortName"
+/>
+
+
+
+ class: the fully qualified class name
+ of any Java class.
+
+
+
+ rename (optional - defaults to the
+ unqualified class name): a name that can be used in the query
+ language.
+
+
+
+
+
+ This feature is unique to hbm.xml and is not supported in
+ annotations.
+
+
+
+
+ Column and formula elements
+
+ Mapping elements which accept a column
+ attribute will alternatively accept a
+ <column> subelement. Likewise,
+ <formula> is an alternative to the
+ formula attribute. For example:
+
+ <column
+ name="column_name"
+ length="N"
+ precision="N"
+ scale="N"
+ not-null="true|false"
+ unique="true|false"
+ unique-key="multicolumn_unique_key_name"
+ index="index_name"
+ sql-type="sql_type_name"
+ check="SQL expression"
+ default="SQL expression"
+ read="SQL expression"
+ write="SQL expression"/>
+
+ <formula>SQL expression</formula>
+
+ Most of the attributes on column provide a
+ means of tailoring the DDL during automatic schema generation. The
+ read and write attributes allow
+ you to specify custom SQL that Hibernate will use to access the
+ column's value. For more on this, see the discussion of column read and write
+ expressions.
+
+ The column and formula
+ elements can even be combined within the same property or association
+ mapping to express, for example, exotic join conditions.
+
+ <many-to-one name="homeAddress" class="Address"
+ insert="false" update="false">
+ <column name="person_id" not-null="true" length="10"/>
+ <formula>'MAILING'</formula>
+</many-to-one>
+
+