Author: steve.ebersole(a)jboss.com
Date: 2010-02-24 16:26:24 -0500 (Wed, 24 Feb 2010)
New Revision: 18874
Added:
core/trunk/entitymanager/src/main/docbook/en/modules/metamodel.xml
Modified:
core/trunk/entitymanager/src/main/docbook/en/master.xml
Log:
HHH-4949 - Document JPA 2 metamodel
Modified: core/trunk/entitymanager/src/main/docbook/en/master.xml
===================================================================
--- core/trunk/entitymanager/src/main/docbook/en/master.xml 2010-02-24 21:20:26 UTC (rev
18873)
+++ core/trunk/entitymanager/src/main/docbook/en/master.xml 2010-02-24 21:26:24 UTC (rev
18874)
@@ -70,6 +70,7 @@
<xi:include
xmlns:xi="http://www.w3.org/2001/XInclude"
href="modules/architecture.xml"/>
<xi:include
xmlns:xi="http://www.w3.org/2001/XInclude"
href="modules/configuration.xml"/>
<xi:include
xmlns:xi="http://www.w3.org/2001/XInclude"
href="modules/entitymanagerapi.xml"/>
+ <xi:include
xmlns:xi="http://www.w3.org/2001/XInclude"
href="modules/metamodel.xml"/>
<xi:include
xmlns:xi="http://www.w3.org/2001/XInclude"
href="modules/transactions.xml"/>
<xi:include
xmlns:xi="http://www.w3.org/2001/XInclude"
href="modules/listeners.xml"/>
<xi:include
xmlns:xi="http://www.w3.org/2001/XInclude"
href="modules/batch.xml"/>
Added: core/trunk/entitymanager/src/main/docbook/en/modules/metamodel.xml
===================================================================
--- core/trunk/entitymanager/src/main/docbook/en/modules/metamodel.xml
(rev 0)
+++ core/trunk/entitymanager/src/main/docbook/en/modules/metamodel.xml 2010-02-24 21:26:24
UTC (rev 18874)
@@ -0,0 +1,240 @@
+<?xml version='1.0' encoding='UTF-8'?>
+<!--
+ ~ Hibernate, Relational Persistence for Idiomatic Java
+ ~
+ ~ Copyright (c) 2010, Red Hat Inc. or third-party contributors as
+ ~ indicated by the @author tags or express copyright attribution
+ ~ statements applied by the authors. All third-party contributions are
+ ~ distributed under license by Red Hat Inc.
+ ~
+ ~ This copyrighted material is made available to anyone wishing to use, modify,
+ ~ copy, or redistribute it subject to the terms and conditions of the GNU
+ ~ Lesser General Public License, as published by the Free Software Foundation.
+ ~
+ ~ This program is distributed in the hope that it will be useful,
+ ~ but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ ~ or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
+ ~ for more details.
+ ~
+ ~ You should have received a copy of the GNU Lesser General Public License
+ ~ along with this distribution; if not, write to:
+ ~ Free Software Foundation, Inc.
+ ~ 51 Franklin Street, Fifth Floor
+ ~ Boston, MA 02110-1301 USA
+ -->
+<!DOCTYPE chapter PUBLIC "-//OASIS//DTD DocBook XML V4.5//EN"
"http://www.oasis-open.org/docbook/xml/4.5/docbookx.dtd" [
+<!ENTITY jpa2Biblio '<xref linkend="JPA2"/>'>
+<!ENTITY jpa2Cite '<citation>&jpa2Biblio;</citation>'>
+<!ENTITY criteriaRef '<xref linkend="querycriteria"/>'>
+<!ENTITY apt '<ulink
url="http://java.sun.com/javase/6/docs/technotes/tools/solaris/javac...
processor</ulink>'>
+]>
+
+<chapter id="metamodel">
+ <title>Metamodel</title>
+
+ <note>
+ <para>
+ The Metamodel itself is described in <citetitle
pubwork="chapter">Chapter 5 Metamodel API</citetitle>
+ of the &jpa2Cite;. <citetitle pubwork="chapter">Chapter
6 Criteria API</citetitle> of the &jpa2Cite;
+ describes and shows uses of the metamodel in criteria queries, as does
&criteriaRef;.
+ </para>
+ </note>
+
+ <para>
+ The metamodel is a set of objects that describe your domain model.
+ <interfacename>javax.persistence.metamodel.Metamodel</interfacename>
acts as a repository of these metamodel
+ objects and provides access to them. We ask either the
+ <interfacename>javax.persistence.EntityManagerFactory</interfacename>
or the
+ <interfacename>javax.persistence.EntityManager</interfacename> for a
reference to the
+ <interfacename>javax.persistence.metamodel.Metamodel</interfacename>
via their
+ <methodname>getMetamodel</methodname> method.
+ </para>
+
+ <para>
+ This metamodel is important in 2 ways. First, it allows providers and frameworks
a generic way to
+ deal with an application's domain model. Persistence providers will already
have some form of
+ metamodel that they use to describe the domain model being mapped. This API
simply allows general access
+ to that existing information. A validation framework, for example, could use
this information to
+ understand associations; a marshaling framework might use this information to
decide how much of an
+ entity graph to marshal. This usage is beyond the scope of this documentation.
+ </para>
+
+ <important>
+ <para>
+ As of today the JPA 2 metamodel does not provide any facility for accessing
relational information
+ pertaining to the physical model. It is expected this will be addressed in a
future release of the
+ specification.
+ </para>
+ </important>
+
+ <para>
+ Second, from an application writer's perspective, it allows very fluent
expression of completely type-safe
+ criteria queries, especially the <emphasis>Static
Metamodel</emphasis> approach. The &jpa2Cite; defines a
+ number of ways the metamodel can be accessed and used, including the
<emphasis>Static Metamodel</emphasis>
+ approach, which we will look at later. The <emphasis>Static
Metamodel</emphasis> approach is wonderful
+ when the code has <ulink
url="http://en.wikipedia.org/wiki/A_priori_and_a_posteriori">a priori
knowledge</ulink>
+ of the domain model. &criteriaRef; uses this approach exclusively in its
examples.
+ </para>
+
+ <section id="metamodel-static">
+ <title>Static metamodel</title>
+ <para>
+ A <emphasis>static metamodel</emphasis> is a series of classes
that "mirror" the entities and embeddables
+ in the domain model and provide static access to the metadata about the
mirrored class's attributes. We
+ will exclusively discuss what the &jpa2Cite; terms a
<emphasis>Canonical Metamodel</emphasis>:
+ </para>
+
+ <blockquote>
+ <attribution>
+ <citation><xref linkend="JPA2"/>, section 6.2.1.1,
pp 198-199</citation>
+ </attribution>
+ <para>
+ <itemizedlist>
+ <listitem>
+ <para>
+ For each managed class <classname>X</classname>
in package <package>p</package>,
+ a metamodel class <classname>X_</classname> in
package <package>p</package> is created.
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+ The name of the metamodel class is derived from the name of
the managed class by appending
+ "_" to the name of the managed class.
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+ The metamodel class <classname>X_</classname>
must be annotated with the
+
<interfacename>javax.persistence.StaticMetamodel</interfacename>annotation
+ <footnote>
+ <para>
+ <emphasis>(from the original)</emphasis>
If the class was generated, the
+
<interfacename>javax.annotation.Generated</interfacename> annotation should
be
+ used to annotate the class. The use of any other
annotations on static metamodel
+ classes is undefined.
+ </para>
+ </footnote>
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+ If class <classname>X</classname> extends another
class <classname>S</classname>, where
+ <classname>S</classname> is the most derived
managed class (i.e., entity or mapped
+ superclass) extended by <classname>X</classname>,
then class <classname>X_</classname> must
+ extend class <classname>S_</classname>, where
<classname>S_</classname> is the metamodel
+ class created for <classname>S</classname>.
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+ For every persistent non-collection-valued attribute
<emphasis>y</emphasis> declared by
+ class <classname>X</classname>, where the type of
<emphasis>y</emphasis> is
+ <classname>Y</classname>, the metamodel class
must contain a declaration as follows:
+ <programlisting><![CDATA[public static volatile
SingularAttribute<X, Y> y;]]></programlisting>
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+ For every persistent collection-valued attribute
<emphasis>z</emphasis> declared by class
+ <classname>X</classname>, where the element type
of <emphasis>z</emphasis> is
+ <classname>Z</classname>, the metamodel class
must contain a declaration as follows:
+ <itemizedlist>
+ <listitem>
+ <para>
+ if the collection type of
<emphasis>z</emphasis> is
+
<interfacename>java.util.Collection</interfacename>, then
+ <programlisting><![CDATA[public static
volatile CollectionAttribute<X, Z> z;]]></programlisting>
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+ if the collection type of
<emphasis>z</emphasis> is
+
<interfacename>java.util.Set</interfacename>, then
+ <programlisting><![CDATA[public static
volatile SetAttribute<X, Z> z;]]></programlisting>
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+ if the collection type of
<emphasis>z</emphasis> is
+
<interfacename>java.util.List</interfacename>, then
+ <programlisting><![CDATA[public static
volatile ListAttribute<X, Z> z;]]></programlisting>
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+ if the collection type of
<emphasis>z</emphasis> is
+
<interfacename>java.util.Map</interfacename>, then
+ <programlisting><![CDATA[public static
volatile MapAttribute<X, K, Z> z;]]></programlisting>
+ where <classname>K</classname> is the
type of the key of the map in class
+ <classname>X</classname>
+ </para>
+ </listitem>
+ </itemizedlist>
+ </para>
+ </listitem>
+ </itemizedlist>
+ </para>
+ <para>
+ Import statements must be included for the needed
<package>javax.persistence.metamodel</package> types
+ as appropriate (e.g.,
<interfacename>javax.persistence.metamodel.SingularAttribute</interfacename>,
+
<interfacename>javax.persistence.metamodel.CollectionAttribute</interfacename>,
+
<interfacename>javax.persistence.metamodel.SetAttribute</interfacename>,
+
<interfacename>javax.persistence.metamodel.ListAttribute</interfacename>,
+
<interfacename>javax.persistence.metamodel.MapAttribute</interfacename>) and
all classes
+ <classname>X</classname>,
<classname>Y</classname>, <classname>Z</classname>, and
<classname>K</classname>.
+ </para>
+ </blockquote>
+
+ <example id="metamodel-static-ex">
+ <title>Static metamodel example</title>
+ <para>
+ For the <classname>Person</classname> entity
+ <programlisting><![CDATA[package
org.hibernate.jpa2.metamodel.example;
+
+import java.util.Set;
+import javax.persistence.Entity;
+
+@Entity
+public class Person {
+ @Id private Long id;
+ private String name;
+ private int age;
+ private Address address;
+ @OneToMany private Set<Order> orders;
+}]]></programlisting>
+ The corresponding canonical metamodel class,
<classname>Person_</classname> would look like
+ <programlisting><![CDATA[package
org.hibernate.jpa2.metamodel.example;
+
+import javax.persistence.metamodel.SingularAttribute;
+import javax.persistence.metamodel.SetAttribute;
+import javax.persistence.metamodel.StaticMetamodel;
+
+@StaticMetamodel( Person.class )
+public class Person_ {
+ public static volatile SingularAttribute<Person, Long> id;
+ public static volatile SingularAttribute<Person, String> name;
+ public static volatile SingularAttribute<Person, Integer> age;
+ public static volatile SingularAttribute<Person, Address> address;
+ public static volatile SetAttribute<Person, Order> orders;
+}]]></programlisting>
+ </para>
+ </example>
+
+ <note>
+ <para>
+ These canonical metamodel classes can be generated manually if you wish
though it is expected
+ that most developers will prefer use of an &apt;. Although
annotation processors themselves are
+ beyond the scope of this document, the Hibernate team does develop an
annotation processor tool for
+ generating a canonical metamodel. See <citetitle>Hibernate
Metamodel Generator</citetitle>.
+ </para>
+ </note>
+
+ <para>
+ When the Hibernate
<interfacename>EntityManagerFactory</interfacename> is being built, it will
+ look for a canonical metamodel class for each of the managed typed is knows
about and if it finds
+ any it will inject the appropriate metamodel information into them, as
outlined in
+ <citation><xref linkend="JPA2"/>, section 6.2.2, pg
200</citation>
+ </para>
+ </section>
+
+</chapter>
\ No newline at end of file