adding batch-fetch and database-partitioning examples
diff --git a/batch-fetch/.classpath b/batch-fetch/.classpath
new file mode 100644
index 0000000..4e2db7c
--- /dev/null
+++ b/batch-fetch/.classpath
@@ -0,0 +1,12 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<classpath>
+	<classpathentry kind="src" path="src"/>
+	<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER"/>
+	<classpathentry kind="con" path="org.eclipse.jdt.USER_LIBRARY/EclipseLink 1.2">
+		<attributes>
+			<attribute name="owner.project.facets" value="jpt.jpa;#system#"/>
+		</attributes>
+	</classpathentry>
+	<classpathentry kind="con" path="org.eclipse.jdt.USER_LIBRARY/Oracle JDBC"/>
+	<classpathentry kind="output" path="classes"/>
+</classpath>
diff --git a/batch-fetch/.project b/batch-fetch/.project
new file mode 100644
index 0000000..9c634b1
--- /dev/null
+++ b/batch-fetch/.project
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<projectDescription>
+	<name>org.eclipse.persistence.example.jpa.batch-fetch</name>
+	<comment></comment>
+	<projects>
+	</projects>
+	<buildSpec>
+		<buildCommand>
+			<name>org.eclipse.jdt.core.javabuilder</name>
+			<arguments>
+			</arguments>
+		</buildCommand>
+		<buildCommand>
+			<name>org.eclipse.wst.common.project.facet.core.builder</name>
+			<arguments>
+			</arguments>
+		</buildCommand>
+		<buildCommand>
+			<name>org.eclipse.wst.validation.validationbuilder</name>
+			<arguments>
+			</arguments>
+		</buildCommand>
+	</buildSpec>
+	<natures>
+		<nature>org.eclipse.wst.common.project.facet.core.nature</nature>
+		<nature>org.eclipse.jdt.core.javanature</nature>
+		<nature>org.eclipse.wst.common.modulecore.ModuleCoreNature</nature>
+		<nature>org.eclipse.jem.workbench.JavaEMFNature</nature>
+	</natures>
+</projectDescription>
diff --git a/batch-fetch/batch-fetch.zip b/batch-fetch/batch-fetch.zip
new file mode 100644
index 0000000..66f48f3
--- /dev/null
+++ b/batch-fetch/batch-fetch.zip
Binary files differ
diff --git a/batch-fetch/build.xml b/batch-fetch/build.xml
new file mode 100644
index 0000000..da9ad22
--- /dev/null
+++ b/batch-fetch/build.xml
@@ -0,0 +1,48 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project basedir="." default="build" name="org.eclipse.persistence.example.jpa.batch-fetch">
+    <property environment="env"/>
+    <property name="JDBC_LIB" value="./ojdbc6.jar"/>
+    <property name="JPA_LIB" value="./persistence.jar"/>
+    <property name="ECLIPSELINK_LIB" value="./eclipselink.jar"/>
+    <property name="AGENT" value="-javaagent:${ECLIPSELINK_LIB}"/>
+    <property name="debuglevel" value="source,lines,vars"/>
+    <path id="example.classpath">
+        <pathelement location="classes"/>
+        <pathelement location="${JDBC_LIB}"/>
+        <pathelement location="${JPA_LIB}"/>
+        <pathelement location="${ECLIPSELINK_LIB}"/>
+    </path>
+    <target name="init" depends="clean">
+        <mkdir dir="classes"/>
+    </target>
+    <target name="clean">
+        <delete dir="classes"/>
+    </target>
+
+    <target depends="init" name="build">
+        <echo message="${ant.project.name}: ${ant.file}"/>
+        <javac debug="true" debuglevel="${debuglevel}" destdir="classes">
+            <src path="src"/>
+            <exclude name="**/.svn/**"/>
+            <classpath refid="example.classpath"/>
+        </javac>
+        <copy file="src/META-INF/persistence.xml" todir="classes/META-INF"/>
+    </target>
+
+    <target name="populate" depends="build">
+        <java classname="example.Populate"
+                fork="true">
+               <jvmarg value="${AGENT}"/>
+            <classpath refid="example.classpath"/>
+        </java>
+    </target>
+
+    <target name="queries" depends="build">
+        <java classname="example.Queries"
+                maxmemory="512m"
+                fork="true">
+               <jvmarg value="${AGENT}"/>
+            <classpath refid="example.classpath"/>
+        </java>
+    </target>
+</project>
diff --git a/batch-fetch/src/META-INF/persistence.xml b/batch-fetch/src/META-INF/persistence.xml
new file mode 100644
index 0000000..5bef3b8
--- /dev/null
+++ b/batch-fetch/src/META-INF/persistence.xml
@@ -0,0 +1,69 @@
+<?xml version="1.0" encoding="UTF-8" ?>
+<persistence xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+        xsi:schemaLocation="http://java.sun.com/xml/ns/persistence http://java.sun.com/xml/ns/persistence/persistence_2_0.xsd"
+        version="2.0" xmlns="http://java.sun.com/xml/ns/persistence">
+    <persistence-unit name="employee" transaction-type="RESOURCE_LOCAL">
+        <class>model.SmallProject</class>
+        <class>model.Project</class>
+        <class>model.PhoneNumber</class>
+        <class>model.LargeProject</class>
+        <class>model.EmploymentPeriod</class>
+        <class>model.Employee</class>
+        <class>model.Address</class>
+        <class>model.EmailAddress</class>
+        <class>model.JobTitle</class>
+        <class>model.Degree</class>
+        <properties>
+            <!-- Default database login using Oracle for EclipseLink's internal connection pool,
+                 change this to access your own database. -->
+            <property name="javax.persistence.jdbc.driver" value="oracle.jdbc.OracleDriver" />
+            <property name="javax.persistence.jdbc.url" value="jdbc:oracle:thin:@localhost:1521:orcl" />
+            <property name="javax.persistence.jdbc.user" value="scott" />
+            <property name="javax.persistence.jdbc.password" value="tiger" />
+
+            <!-- The database platform is auto-detected by default,
+                 if you want to set a specific platform this can be set. -->
+            <!-- property name=""eclipselink.target-database" value="Oracle" / -->
+
+            <!-- Optimize database writes to use batching. -->
+            <!-- property name="eclipselink.jdbc.batch-writing" value="JDBC" / -->
+            
+            <!-- Avoids flush being triggered before every query execution. -->
+            <property name="eclipselink.persistence-context.flush-mode" value="COMMIT" />
+
+            <!-- Configure connection pool. -->
+            <property name="eclipselink.jdbc.connections.initial" value="1" />
+            <property name="eclipselink.jdbc.connections.min" value="64" />
+            <property name="eclipselink.jdbc.connections.max" value="64" />
+            
+            <!-- Enabled statement caching, this is only required when using internal connection pooling,
+                 when using a DataSource, statement caching must be configured in the DataSource. -->
+            <property name="eclipselink.jdbc.cache-statements" value="true" />
+
+            <!-- In JSE no server platform is used, if you wish to use this example is a JEE server with JTA,
+                             then you need to set this. -->
+            <!-- property name="eclipselink.target-server" value="WebLogic" / -->
+
+            <!-- Configure cache size. -->
+            <property name="eclipselink.cache.size.default" value="1000" />
+            <!-- If desired, this option would disable caching. -->
+            <!-- property name="eclipselink.cache.shared.default" value="false" / -->
+
+            <!-- If desired, this option would force a JDBC connection to be held for the duration of an EntityManager,
+                 instead of returned to the pool in between queries/transactions. -->
+            <!-- property name="eclipselink.jdbc.exclusive-connection.mode" value="Always" / -->
+
+            <!-- Configure database to be created on startup if not already existing. -->
+            <!-- property name="eclipselink.ddl-generation" value="create-tables" / -->
+            <!-- To drop and replace existing schema this can be used. -->
+            <property name="eclipselink.ddl-generation" value="drop-and-create-tables" />
+
+            <!-- Configure simple SQL logging for demonstration. -->
+            <!-- property name="eclipselink.logging.level" value="FINE" / -->
+            <property name="eclipselink.logging.thread" value="false" />
+            <property name="eclipselink.logging.session" value="false" />
+            <property name="eclipselink.logging.exceptions" value="false" />
+            <property name="eclipselink.logging.timestamp" value="false" />
+        </properties>
+    </persistence-unit>
+</persistence>
diff --git a/batch-fetch/src/example/Populate.java b/batch-fetch/src/example/Populate.java
new file mode 100644
index 0000000..7249d1e
--- /dev/null
+++ b/batch-fetch/src/example/Populate.java
@@ -0,0 +1,642 @@
+/*******************************************************************************
+ * Copyright (c) 1998, 2012 Oracle and/or its affiliates. All rights reserved.
+ * This program and the accompanying materials are made available under the 
+ * terms of the Eclipse Public License v1.0 and Eclipse Distribution License v. 1.0 
+ * which accompanies this distribution. 
+ * The Eclipse Public License is available at http://www.eclipse.org/legal/epl-v10.html
+ * and the Eclipse Distribution License is available at 
+ * http://www.eclipse.org/org/documents/edl-v10.php.
+ *
+ * Contributors:
+ *              dclarke - initial JPA Employee example using XML (bug 217884)
+ ******************************************************************************/
+package example;
+
+import javax.persistence.EntityManager;
+import javax.persistence.EntityManagerFactory;
+import javax.persistence.Persistence;
+import javax.persistence.Query;
+import javax.persistence.criteria.CriteriaBuilder;
+import javax.persistence.criteria.CriteriaQuery;
+import javax.persistence.criteria.Root;
+
+import model.*;
+
+/**
+ * This example populates the database with example instances using JPA.
+ */
+public class Populate {
+
+    public static void main(String[] args) {
+        EntityManagerFactory emf = Persistence.createEntityManagerFactory("employee");
+        populate(emf);
+        emf.close();
+    }
+
+    public static void populate(EntityManagerFactory emf) {
+        EntityManager em = emf.createEntityManager();
+        em.getTransaction().begin();
+        population = new Populate();
+        Populate.population.persistAll(em);
+        em.getTransaction().commit();
+        em.close();
+    }
+
+    public static Populate population = new Populate();
+
+    public Employee[] employees = { basicEmployeeExample1(), basicEmployeeExample2(), basicEmployeeExample3(), basicEmployeeExample4(), basicEmployeeExample5(), basicEmployeeExample6(),
+            basicEmployeeExample7(), basicEmployeeExample8(), basicEmployeeExample9(), basicEmployeeExample10(), basicEmployeeExample11(), basicEmployeeExample12() };
+
+    private SmallProject[] smallProjects = { basicSmallProjectExample1(), basicSmallProjectExample2(), basicSmallProjectExample3(), basicSmallProjectExample4(), basicSmallProjectExample5(),
+            basicSmallProjectExample7(), basicSmallProjectExample8(), basicSmallProjectExample9(), basicSmallProjectExample10() };
+
+    private LargeProject[] largeProjects = { basicLargeProjectExample1(), basicLargeProjectExample2(), basicLargeProjectExample3(), basicLargeProjectExample4(), basicLargeProjectExample5() };
+
+    private JobTitle[] jobTitles = { new JobTitle("CEO"), new JobTitle("VP"), new JobTitle("Manager"), new JobTitle("Developer"), new JobTitle("Admin") };
+
+    private Populate() {
+
+        // Setup management hierarchy
+        addManagedEmployees(0, new int[] { 2, 3, 4 });
+        setJobTitle(0, 2);
+        addManagedEmployees(1, new int[] { 5, 0 });
+        setJobTitle(1, 2);
+        addManagedEmployees(2, new int[] {});
+        setJobTitle(0, 3);
+        addManagedEmployees(3, new int[] {});
+        setJobTitle(0, 3);
+        addManagedEmployees(4, new int[] {});
+        setJobTitle(0, 3);
+        addManagedEmployees(5, new int[] {});
+        setJobTitle(5, 4);
+        addManagedEmployees(6, new int[] {});
+        setJobTitle(6, 4);
+        addManagedEmployees(7, new int[] {});
+        setJobTitle(7, 1);
+        addManagedEmployees(8, new int[] {});
+        setJobTitle(8, 4);
+        addManagedEmployees(9, new int[] { 7, 8, 10, 11 });
+        setJobTitle(9, 0);
+        addManagedEmployees(10, new int[] { 6 });
+        setJobTitle(10, 1);
+        addManagedEmployees(11, new int[] { 1 });
+        setJobTitle(11, 1);
+
+        // Setup Employee-Project associations
+        addProjects(0, new int[] { 0, 1, 2 }, new int[] {});
+        addProjects(1, new int[] { 3, 4, 0 }, new int[] {});
+        addProjects(2, new int[] { 3 }, new int[] { 3, 4 });
+        addProjects(4, new int[] { 3, 1 }, new int[] { 2, 4 });
+        addProjects(5, new int[] {}, new int[] { 1 });
+        addProjects(6, new int[] {}, new int[] { 1 });
+
+        // Setup LargeProject leads
+        this.largeProjects[0].setTeamLeader(this.employees[1]);
+        this.largeProjects[3].setTeamLeader(this.employees[2]);
+        this.largeProjects[4].setTeamLeader(this.employees[2]);
+    }
+
+    public Employee basicEmployeeExample1() {
+        Employee employee = new Employee();
+
+        employee.setFirstName("Bob");
+        employee.setLastName("Smith");
+        employee.setGender(Gender.Male);
+        employee.setSalary(35000);
+
+        EmploymentPeriod employmentPeriod = new EmploymentPeriod();
+        employmentPeriod.setEndDate(1996, 0, 1);
+        employmentPeriod.setStartDate(1993, 0, 1);
+        employee.setPeriod(employmentPeriod);
+
+        Address address = new Address();
+        address.setCity("Toronto");
+        address.setPostalCode("L5J2B5");
+        address.setProvince("ONT");
+        address.setStreet("1450 Acme Cr., Suite 4");
+        address.setCountry("Canada");
+        employee.setAddress(address);
+
+        employee.addResponsibility("Water the office plants.");
+        employee.addResponsibility("Maintain the kitchen facilities.");
+        employee.addPhoneNumber("Work", "613", "5558812");
+
+        return employee;
+    }
+
+    public Employee basicEmployeeExample10() {
+        Employee employee = new Employee();
+
+        employee.setFirstName("Jill");
+        employee.setLastName("May");
+        employee.setGender(Gender.Female);
+
+        EmploymentPeriod employmentPeriod = new EmploymentPeriod();
+        employmentPeriod.setStartDate(1991, 10, 11);
+        employee.setPeriod(employmentPeriod);
+
+        Address address = new Address();
+        address.setCity("Calgary");
+        address.setPostalCode("J5J2B5");
+        address.setProvince("AB");
+        address.setStreet("1111 Mooseland Rd.");
+        address.setCountry("Canada");
+        employee.setAddress(address);
+
+        employee.setSalary(56232);
+        employee.addPhoneNumber("Work", "613", "5558812");
+        employee.addPhoneNumber("Work Fax", "613", "5555943");
+        employee.addEmailAddress("Work", "jill.may@acme.com");
+        employee.addEmailAddress("Mobile", "jill.lewis.may@sprint.com");
+        employee.addDegree("Bachelor Computer Science");
+        employee.addDegree("Masters Computer Science");
+        employee.addDegree("PHD Computer Science");
+
+        return employee;
+    }
+
+    public Employee basicEmployeeExample11() {
+        Employee employee = new Employee();
+
+        employee.setFirstName("Sarah-Lou");
+        employee.setLastName("Smitty");
+        employee.setGender(Gender.Female);
+
+        EmploymentPeriod employmentPeriod = new EmploymentPeriod();
+        employmentPeriod.setEndDate(1996, 0, 1);
+        employmentPeriod.setStartDate(1993, 0, 1);
+        employee.setPeriod(employmentPeriod);
+
+        Address address = new Address();
+        address.setCity("Arnprior");
+        address.setPostalCode("W1A2B5");
+        address.setProvince("ONT");
+        address.setStreet("1 Hawthorne Drive");
+        address.setCountry("Canada");
+        employee.setAddress(address);
+
+        employee.setSalary(75000);
+        employee.addPhoneNumber("Work Fax", "613", "5555943");
+        employee.addPhoneNumber("Home", "613", "5551234");
+        employee.addPhoneNumber("Cellular", "416", "5551111");
+        employee.addEmailAddress("Home", "sarah-lou.smitty@rogers.com");
+        employee.addDegree("Bachelor Computer Science");
+
+        return employee;
+    }
+
+    public Employee basicEmployeeExample12() {
+        Employee employee = new Employee();
+
+        employee.setFirstName("Jim-Bob");
+        employee.setLastName("Jefferson");
+        employee.setGender(Gender.Male);
+
+        EmploymentPeriod employmentPeriod = new EmploymentPeriod();
+        employmentPeriod.setEndDate(2001, 11, 31);
+        employmentPeriod.setStartDate(1995, 0, 12);
+        employee.setPeriod(employmentPeriod);
+
+        Address address = new Address();
+        address.setCity("Yellowknife");
+        address.setPostalCode("Y5J2N5");
+        address.setProvince("YK");
+        address.setStreet("1112 Gold Rush Rd.");
+        address.setCountry("Canada");
+        employee.setAddress(address);
+
+        employee.setSalary(50000);
+        employee.addPhoneNumber("Home", "613", "5551234");
+        employee.addPhoneNumber("Cellular", "416", "5551111");
+        employee.addEmailAddress("Home", "jim-bob@jim-bob.com");
+
+        return employee;
+    }
+
+    public Employee basicEmployeeExample2() {
+        Employee employee = new Employee();
+
+        employee.setFirstName("John");
+        employee.setLastName("Way");
+        employee.setGender(Gender.Male);
+        employee.setSalary(53000);
+
+        EmploymentPeriod employmentPeriod = new EmploymentPeriod();
+        employmentPeriod.setStartDate(1991, 10, 11);
+        employee.setPeriod(employmentPeriod);
+
+        Address address = new Address();
+        address.setCity("Ottawa");
+        address.setPostalCode("K5J2B5");
+        address.setProvince("ONT");
+        address.setStreet("12 Merivale Rd., Suite 5");
+        address.setCountry("Canada");
+        employee.setAddress(address);
+
+        employee.addResponsibility("Hire people when more people are required.");
+        employee.addResponsibility("Lay off employees when less people are required.");
+        employee.addPhoneNumber("Work", "613", "5558812");
+        employee.addPhoneNumber("ISDN", "905", "5553691");
+        employee.addEmailAddress("Work", "john.way@acme.com");
+        employee.addDegree("Bachelor Computer Science");
+
+        return employee;
+    }
+
+    public Employee basicEmployeeExample3() {
+        Employee employee = new Employee();
+
+        employee.setFirstName("Charles");
+        employee.setLastName("Chanley");
+        employee.setGender(Gender.Male);
+        employee.setSalary(43000);
+
+        EmploymentPeriod employmentPeriod = new EmploymentPeriod();
+        employmentPeriod.setEndDate(2001, 11, 31);
+        employmentPeriod.setStartDate(1995, 0, 1);
+        employee.setPeriod(employmentPeriod);
+
+        Address address = new Address();
+        address.setCity("Montreal");
+        address.setPostalCode("Q2S5Z5");
+        address.setProvince("QUE");
+        address.setStreet("1 Canadien Place");
+        address.setCountry("Canada");
+        employee.setAddress(address);
+
+        employee.addResponsibility("Perform code reviews as required.");
+        employee.addPhoneNumber("Pager", "976", "5556666");
+        employee.addPhoneNumber("ISDN", "905", "5553691");
+        employee.addEmailAddress("Work", "charles.chanley@acme.com");
+
+        return employee;
+    }
+
+    public Employee basicEmployeeExample4() {
+        Employee employee = new Employee();
+
+        employee.setFirstName("Emanual");
+        employee.setLastName("Smith");
+        employee.setGender(Gender.Male);
+        employee.setSalary(49631);
+
+        EmploymentPeriod employmentPeriod = new EmploymentPeriod();
+        employmentPeriod.setEndDate(2001, 11, 31);
+        employmentPeriod.setStartDate(1995, 0, 1);
+        employee.setPeriod(employmentPeriod);
+
+        Address address = new Address();
+        address.setCity("Vancouver");
+        address.setPostalCode("N5J2N5");
+        address.setProvince("BC");
+        address.setStreet("20 Mountain Blvd., Floor 53, Suite 6");
+        address.setCountry("Canada");
+        employee.setAddress(address);
+
+        employee.addResponsibility("Have to fix the Database problem.");
+        employee.addPhoneNumber("Work Fax", "613", "5555943");
+        employee.addPhoneNumber("Cellular", "416", "5551111");
+        employee.addPhoneNumber("Pager", "976", "5556666");
+        employee.addPhoneNumber("ISDN", "905", "5553691");
+        employee.addEmailAddress("Work", "emanual.smith@acme.com");
+
+        return employee;
+    }
+
+    public Employee basicEmployeeExample5() {
+        Employee employee = new Employee();
+
+        employee.setFirstName("Sarah");
+        employee.setLastName("Way");
+        employee.setGender(Gender.Female);
+        employee.setSalary(87000);
+
+        EmploymentPeriod employmentPeriod = new EmploymentPeriod();
+        employmentPeriod.setEndDate(2001, 6, 31);
+        employmentPeriod.setStartDate(1995, 4, 1);
+        employee.setPeriod(employmentPeriod);
+
+        Address address = new Address();
+        address.setCity("Prince Rupert");
+        address.setPostalCode("K3K5D5");
+        address.setProvince("BC");
+        address.setStreet("3254 Parkway Place");
+        address.setCountry("Canada");
+        employee.setAddress(address);
+
+        employee.addResponsibility("Write code documentation.");
+        employee.addPhoneNumber("Work", "613", "5558812");
+        employee.addPhoneNumber("ISDN", "905", "5553691");
+        employee.addPhoneNumber("Home", "613", "5551234");
+        employee.addEmailAddress("Work", "sarah.way@acme.com");
+
+        return employee;
+    }
+
+    public Employee basicEmployeeExample6() {
+        Employee employee = new Employee();
+
+        employee.setFirstName("Marcus");
+        employee.setLastName("Saunders");
+        employee.setGender(Gender.Male);
+        employee.setSalary(54300);
+
+        EmploymentPeriod employmentPeriod = new EmploymentPeriod();
+        employmentPeriod.setEndDate(2001, 11, 31);
+        employmentPeriod.setStartDate(1995, 0, 12);
+        employee.setPeriod(employmentPeriod);
+
+        Address address = new Address();
+        address.setCity("Perth");
+        address.setPostalCode("Y3Q2N9");
+        address.setProvince("ONT");
+        address.setStreet("234 Caledonia Lane");
+        address.setCountry("Canada");
+        employee.setAddress(address);
+
+        employee.addResponsibility("Write user specifications.");
+        employee.addPhoneNumber("ISDN", "905", "5553691");
+        employee.addPhoneNumber("Work", "613", "5558812");
+        employee.addEmailAddress("Work", "marcus.saunders@acme.com");
+        employee.addDegree("Bachelor Computer Science");
+        employee.addDegree("Masters Computer Science");
+
+        return employee;
+    }
+
+    public Employee basicEmployeeExample7() {
+        Employee employee = new Employee();
+
+        employee.setFirstName("Nancy");
+        employee.setLastName("White");
+        employee.setGender(Gender.Female);
+        employee.setSalary(31000);
+
+        EmploymentPeriod employmentPeriod = new EmploymentPeriod();
+        employmentPeriod.setEndDate(1996, 0, 1);
+        employmentPeriod.setStartDate(1993, 0, 1);
+        employee.setPeriod(employmentPeriod);
+
+        Address address = new Address();
+        address.setCity("Metcalfe");
+        address.setPostalCode("Y4F7V6");
+        address.setProvince("ONT");
+        address.setStreet("2 Anderson Rd.");
+        address.setCountry("Canada");
+        employee.setAddress(address);
+
+        employee.addPhoneNumber("Home", "613", "5551234");
+        employee.addEmailAddress("Work", "nancy.white@acme.com");
+
+        return employee;
+    }
+
+    public Employee basicEmployeeExample8() {
+        Employee employee = new Employee();
+
+        employee.setFirstName("Fred");
+        employee.setLastName("Jones");
+        employee.setGender(Gender.Male);
+        employee.setSalary(500000);
+
+        EmploymentPeriod employmentPeriod = new EmploymentPeriod();
+        employmentPeriod.setEndDate(2001, 11, 31);
+        employmentPeriod.setStartDate(1995, 0, 1);
+        employee.setPeriod(employmentPeriod);
+
+        Address address = new Address();
+        address.setCity("Victoria");
+        address.setPostalCode("Z5J2N5");
+        address.setProvince("BC");
+        address.setStreet("382 Hyde Park Blvd.");
+        address.setCountry("Canada");
+        employee.setAddress(address);
+
+        employee.addPhoneNumber("Cellular", "416", "5551111");
+        employee.addPhoneNumber("ISDN", "905", "5553691");
+        employee.addEmailAddress("Work", "fred.jones@acme.com");
+        employee.addDegree("Bachelor Business");
+        employee.addDegree("Masters Business");
+
+        return employee;
+    }
+
+    public Employee basicEmployeeExample9() {
+        Employee employee = new Employee();
+
+        employee.setFirstName("Betty");
+        employee.setLastName("Jones");
+        employee.setGender(Gender.Female);
+        employee.setSalary(500001);
+
+        EmploymentPeriod employmentPeriod = new EmploymentPeriod();
+        employmentPeriod.setStartDate(2001, 11, 31);
+        employmentPeriod.setEndDate(1995, 0, 1);
+        employee.setPeriod(employmentPeriod);
+
+        Address address = new Address();
+        address.setCity("Smith Falls");
+        address.setPostalCode("C6C6C6");
+        address.setProvince("ONT");
+        address.setStreet("89 Chocolate Drive");
+        address.setCountry("Canada");
+        employee.setAddress(address);
+
+        employee.addPhoneNumber("Work", "613", "5558812");
+        employee.addPhoneNumber("ISDN", "905", "5553691");
+        employee.addEmailAddress("Work", "betty.jones@acme.com");
+        employee.addEmailAddress("Home", "betty.cleo.jones@rogers.com");
+        employee.addDegree("Bachelor Arts");
+        employee.addDegree("Masters Engineering");
+        employee.addDegree("PHD Philosophy");
+
+        return employee;
+    }
+
+    public LargeProject basicLargeProjectExample1() {
+        LargeProject largeProject = new LargeProject();
+
+        largeProject.setName("Sales Reporting");
+        largeProject.setDescription("A reporting application to report on the corporations database through TopLink.");
+        largeProject.setBudget((double) 5000);
+        largeProject.getMilestone().set(1991, 10, 11, 12, 0, 0);
+
+        return largeProject;
+    }
+
+    public LargeProject basicLargeProjectExample2() {
+        LargeProject largeProject = new LargeProject();
+
+        largeProject.setName("Light Reporter");
+        largeProject.setDescription("A lightweight application to report on the corporations database through TopLink.");
+        largeProject.setBudget(100.98);
+        largeProject.getMilestone().set(1999, 11, 25, 11, 40, 44);
+
+        return largeProject;
+    }
+
+    public LargeProject basicLargeProjectExample3() {
+        LargeProject largeProject = new LargeProject();
+
+        largeProject.setName("TOPEmployee Management");
+        largeProject.setDescription("A management application to report on the corporations database through TopLink.");
+        largeProject.setBudget(4000.98);
+        largeProject.getMilestone().set(1997, 10, 12, 1, 0, 0);
+
+        return largeProject;
+    }
+
+    public LargeProject basicLargeProjectExample4() {
+        LargeProject largeProject = new LargeProject();
+
+        largeProject.setName("Enterprise System");
+        largeProject.setDescription("A enterprise wide application to report on the corporations database through TopLink.");
+        largeProject.setBudget(40.98);
+        largeProject.getMilestone().set(1996, 8, 6, 6, 40, 44);
+
+        return largeProject;
+    }
+
+    public LargeProject basicLargeProjectExample5() {
+        LargeProject largeProject = new LargeProject();
+
+        largeProject.setName("Problem Reporting System");
+        largeProject.setDescription("A PRS application to report on the corporations database through TopLink.");
+        largeProject.setBudget(101.98);
+        largeProject.getMilestone().set(1997, 9, 6, 1, 40, 44);
+
+        return largeProject;
+    }
+
+    public SmallProject basicSmallProjectExample1() {
+        return new SmallProject("Enterprise", "A enterprise wide application to report on the corporations database through TopLink.");
+    }
+
+    public SmallProject basicSmallProjectExample10() {
+        return new SmallProject("Staff Query Tool", "A tool to help staff query various things.");
+    }
+
+    public SmallProject basicSmallProjectExample2() {
+        return new SmallProject("Sales Reporter", "A reporting application using JDK to report on the corporations database through TopLink.");
+    }
+
+    public SmallProject basicSmallProjectExample3() {
+        return new SmallProject("TOP-Employee Manager", "A management application to report on the corporations database through TopLink.");
+    }
+
+    public SmallProject basicSmallProjectExample4() {
+        return new SmallProject("Problem Reporter", "A PRS application to report on the corporations database through TopLink.");
+    }
+
+    public SmallProject basicSmallProjectExample5() {
+        return new SmallProject("Feather Reporter", "An extremely lightweight application to report on the corporations database through TopLink.");
+    }
+
+    public SmallProject basicSmallProjectExample6() {
+        return new SmallProject("Makework", "A makework project.");
+    }
+
+    public SmallProject basicSmallProjectExample7() {
+        return new SmallProject("Marketing Query Tool", "A tool to help marketing query various things.");
+    }
+
+    public SmallProject basicSmallProjectExample8() {
+        return new SmallProject("Shipping Query Tool", "A tool to help shipping query various things.");
+    }
+
+    public SmallProject basicSmallProjectExample9() {
+        return new SmallProject("Accounting Query Tool", "A tool to help accounting query various things.");
+    }
+
+    private void addManagedEmployees(int managerIndex, int[] employeeIndeces) {
+        Employee manager = this.employees[managerIndex];
+
+        if (manager.getManagedEmployees().isEmpty()) {
+            for (int index = 0; index < employeeIndeces.length; index++) {
+                manager.addManagedEmployee(this.employees[employeeIndeces[index]]);
+            }
+        }
+    }
+
+    private void setJobTitle(int employeeIndex, int jobIndex) {
+        Employee employee = this.employees[employeeIndex];
+
+        employee.setJobTitle(this.jobTitles[jobIndex]);
+    }
+
+    private void addProjects(int empIndex, int[] smallProjIndeces, int[] largeProjIndeces) {
+        Employee employee = this.employees[empIndex];
+
+        for (int index = 0; index < smallProjIndeces.length; index++) {
+            employee.addProject(this.smallProjects[smallProjIndeces[index]]);
+        }
+
+        for (int index = 0; index < largeProjIndeces.length; index++) {
+            employee.addProject(this.largeProjects[largeProjIndeces[index]]);
+        }
+    }
+
+    /**
+     * Register all of the population in the provided EntityManager to be
+     * persisted This method should only be called from within a test case. It
+     * asserts that the provided EntityManager is in a transaction and that the
+     * database tables are empty.
+     */
+    public void persistAll(EntityManager em) {
+        System.out.println("Persisting samples objects.");
+        
+        assert(em.getTransaction().isActive());
+
+        // Verify that the database tables are empty
+        assertCount(em, Employee.class, 0);
+        assertCount(em, Address.class, 0);
+        assertCount(em, PhoneNumber.class, 0);
+        assertCount(em, Project.class, 0);
+        assertCount(em, JobTitle.class, 0);
+
+        for (int index = 0; index < this.jobTitles.length; index++) {
+            em.persist(this.jobTitles[index]);
+        }
+        for (int index = 0; index < this.employees.length; index++) {
+            em.persist(this.employees[index]);
+        }
+        for (int index = 0; index < this.smallProjects.length; index++) {
+            em.persist(this.smallProjects[index]);
+        }
+        for (int index = 0; index < this.largeProjects.length; index++) {
+            em.persist(this.largeProjects[index]);
+        }
+
+        System.out.println("Flushing to database.");
+        em.flush();
+        
+        System.out.println("Verifying populate.");
+        verifyCounts(em);
+    }
+
+    public void verifyCounts(EntityManager em) {
+        assertCount(em, Employee.class, this.employees.length);
+        assertCount(em, Address.class, this.employees.length);
+        assertCount(em, Project.class, this.smallProjects.length + this.largeProjects.length);
+        assertCount(em, JobTitle.class, this.jobTitles.length);
+    }
+
+    /**
+     * Verify that the provided entity type has no rows in the database using a
+     * native ReportQuery.
+     * 
+     * @param entityClass
+     * @param count
+     */
+    public void assertCount(EntityManager em, Class entityClass, int count) {
+        CriteriaBuilder cb = em.getCriteriaBuilder();
+        CriteriaQuery criteria = cb.createQuery();
+        Root entity = criteria.from(entityClass);
+        criteria.select(cb.count(entity));
+        Query query = em.createQuery(criteria);
+
+        Long dbCount = (Long)query.getSingleResult();
+        assert(count == dbCount.intValue());
+    }
+
+}
diff --git a/batch-fetch/src/example/Queries.java b/batch-fetch/src/example/Queries.java
new file mode 100644
index 0000000..5539adc
--- /dev/null
+++ b/batch-fetch/src/example/Queries.java
@@ -0,0 +1,223 @@
+/*******************************************************************************
+ * Copyright (c) 1998, 2012 Oracle and/or its affiliates. All rights reserved.
+ * This program and the accompanying materials are made available under the 
+ * terms of the Eclipse Public License v1.0 and Eclipse Distribution License v. 1.0 
+ * which accompanies this distribution. 
+ * The Eclipse Public License is available at http://www.eclipse.org/legal/epl-v10.html
+ * and the Eclipse Distribution License is available at 
+ * http://www.eclipse.org/org/documents/edl-v10.php.
+ *
+ * Contributors:
+ *              dclarke - initial JPA Employee example using XML (bug 217884)
+ ******************************************************************************/
+package example;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import javax.persistence.EntityManager;
+import javax.persistence.EntityManagerFactory;
+import javax.persistence.Persistence;
+import javax.persistence.Query;
+
+import model.*;
+
+/**
+ * Simple query examples.
+ */
+public class Queries {
+
+    public static int REPEATS = 5;
+    public static int RUN_TIME = 60000; //1 minute.
+
+    /**
+     * Measure the performance of the run.
+     * Repeat the run REPEATS (5) times,
+     * and measure the number of execution in RUN_TIME (60s).
+     */
+    public static void executeRun(String name, Runnable runnable) {
+        System.out.println("Starting run: " + name);
+        
+        List<Integer> results = new ArrayList<Integer>();
+        // Repeat the test and baseline for the number of repeats.
+        for (int index = 0; index < REPEATS; index++) {
+            long startTime, endTime;
+            int executions = 0;
+            System.gc();
+            try {
+                Thread.sleep(1000);
+            } catch (InterruptedException ignore) {}
+            startTime = System.currentTimeMillis();
+            endTime = startTime;
+            // Count how many times the test can be invoked in the run time.
+            // This allows for the test run time to be easily changed.
+            while ((startTime + RUN_TIME) >= endTime) {
+                runnable.run();
+                executions++;
+                endTime = System.currentTimeMillis();
+            }
+            results.add(executions);
+            System.out.println("Done run: " +  index + " for: " + name);
+        }
+        
+        System.out.println("Completed run: " + name);
+
+        System.out.println("");
+        System.out.println(name + " Results");
+        System.out.println("Run repeats:" + REPEATS);
+        System.out.println("Run time:" + RUN_TIME + "ms");
+        System.out.println("Average result:" + averageResults(results));
+        System.out.println("Max result:" + maxResults(results));
+        System.out.println("Min result:" + minResults(results));
+        System.out.println("% standard deviation:" + standardDeviationResults(results));
+        System.out.println("");
+        System.out.println("");        
+    }
+
+    /**
+     * Compute the max of the results.
+     */
+    public static int maxResults(List<Integer> times) {
+        int testMax = 0;
+        for (int index = 0; index < times.size(); index++) {
+            int time = (int)times.get(index);
+            if (time > testMax) {
+                testMax = time;
+            }
+        }
+        return testMax;
+    }
+
+    /**
+     * Compute the min of the results.
+     */
+    public static int minResults(List<Integer> times) {
+        int testMin = 0;
+        for (int index = 0; index < times.size(); index++) {
+            int time = (int)times.get(index);
+            if ((testMin == 0) || (time < testMin)) {
+                testMin = time;
+            }
+        }
+        return testMin;
+    }
+
+    /**
+     * Filter max and min from results.
+     */
+    public static List<Integer> filterMaxMinResults(List<Integer> times) {
+        List filteredTimes = new ArrayList(times);
+        if (filteredTimes.size() > 3) {
+            filteredTimes.remove((Integer)maxResults(times));
+            filteredTimes.remove((Integer)minResults(times));
+        }
+        return filteredTimes;
+    }
+
+    /**
+     * Compute the average of the results rejecting the min and max.
+     */
+    public static double averageResults(List<Integer> allTimes) {
+        // Compute the average reject the min and max to improve consistency.
+        List<Integer> times = filterMaxMinResults(allTimes);
+        double testAverage = 0;
+        for (int index = 0; index < times.size(); index++) {
+            int time = (int)times.get(index);
+            testAverage = testAverage + time;
+        }
+        testAverage = testAverage / times.size();
+        return testAverage;
+    }
+
+    /**
+     * Compute the standard deviation of the results rejecting the min and max.
+     */
+    public static double standardDeviationResults(List<Integer> allTimes) {
+        // Compute the average reject the min and max to improve consistency.
+        double testAverage = averageResults(allTimes);
+
+        // Compute the standard deviation reject the min and max to improve consistency.
+        List<Integer> times = filterMaxMinResults(allTimes);
+        double testStandardDeviation = 0;
+        for (int index = 0; index < times.size(); index++) {
+            int time = (int)times.get(index);
+            testStandardDeviation = testStandardDeviation + Math.pow(time - testAverage, 2);
+        }
+        testStandardDeviation = testStandardDeviation / times.size();
+        testStandardDeviation = Math.sqrt(testStandardDeviation);
+        // As percent of average
+        testStandardDeviation = (testStandardDeviation / testAverage) * 100;
+        return testStandardDeviation;
+    }
+
+
+    public static void main(String[] args) throws Exception {        
+        EntityManagerFactory emf = Persistence.createEntityManagerFactory("employee");
+        //for (int index = 0; index < 5000; index++) {
+            Populate.populate(emf);
+        //}
+        Queries queries = new Queries();
+        queries.clear(emf);
+        queries.runSimpleQuery("standardFindAllBySalary", emf);
+        queries.runSimpleQuery("simpleJoinFetchFindAllBySalary", emf);
+        queries.runSimpleQuery("simpleBatchJOINFetchFindAllBySalary", emf);
+        queries.runSimpleQuery("simpleBatchEXISTSFetchFindAllBySalary", emf);
+        queries.runSimpleQuery("simpleBatchINFetchFindAllBySalary", emf);
+        
+        queries.runComplexQuery("standardFindAllBySalary", emf);
+        queries.runComplexQuery("joinFetchFindAllBySalary", emf);
+        queries.runComplexQuery("batchJOINFetchFindAllBySalary", emf);
+        queries.runComplexQuery("batchEXISTSFetchFindAllBySalary", emf);
+        queries.runComplexQuery("batchINFetchFindAllBySalary", emf);
+        emf.close();
+    }
+
+    public void runSimpleQuery(final String queryName, final EntityManagerFactory emf) {
+        
+        executeRun(queryName, new Runnable() {
+            public void run() {
+                EntityManager em = emf.createEntityManager();
+                Query query = em.createNamedQuery(queryName);
+                query.setParameter("salary", 50000);
+                List<Employee> result = query.getResultList();
+                for (Employee employee : result) {
+                    // Ensure every relationship is accessed.
+                    String.valueOf(employee.getAddress());
+                    employee.getPhoneNumbers().size();
+                }
+                em.close();
+                clear(emf);
+            }
+        });
+    }
+    
+    public void runComplexQuery(final String queryName, final EntityManagerFactory emf) {
+        
+        executeRun(queryName, new Runnable() {
+            public void run() {
+                EntityManager em = emf.createEntityManager();
+                Query query = em.createNamedQuery(queryName);
+                query.setParameter("salary", 50000);
+                List<Employee> result = query.getResultList();
+                for (Employee employee : result) {
+                    // Ensure every relationship is accessed.
+                    String.valueOf(employee.getAddress());
+                    employee.getManagedEmployees().size();
+                    employee.getDegrees().size();
+                    String.valueOf(employee.getManager());
+                    String.valueOf(employee.getJobTitle());
+                    employee.getEmailAddresses().size();
+                    employee.getPhoneNumbers().size();
+                    employee.getProjects().size();
+                    employee.getResponsibilities().size();
+                }
+                em.close();
+                clear(emf);
+            }
+        });
+    }
+    
+    public void clear(EntityManagerFactory factory) {
+        factory.getCache().evictAll();        
+    }
+}
diff --git a/batch-fetch/src/model/Address.java b/batch-fetch/src/model/Address.java
new file mode 100644
index 0000000..3799d9d
--- /dev/null
+++ b/batch-fetch/src/model/Address.java
@@ -0,0 +1,92 @@
+/*******************************************************************************
+ * Copyright (c) 1998, 2012 Oracle and/or its affiliates. All rights reserved.
+ * This program and the accompanying materials are made available under the 
+ * terms of the Eclipse Public License v1.0 and Eclipse Distribution License v. 1.0 
+ * which accompanies this distribution. 
+ * The Eclipse Public License is available at http://www.eclipse.org/legal/epl-v10.html
+ * and the Eclipse Distribution License is available at 
+ * http://www.eclipse.org/org/documents/edl-v10.php.
+ *
+ * Contributors:
+ *              dclarke - initial JPA Employee example using XML (bug 217884)
+ *              mbraeuer - annotated version
+ ******************************************************************************/
+package model;
+
+import java.io.Serializable;
+import javax.persistence.*;
+
+/**
+ * Simple Address class with Basic mappings.
+ * It uses a generated Id.
+ */
+@Entity
+@Table(name="BF_ADDRESS")
+public class Address implements Serializable {
+    @Id
+    @Column(name = "ADDRESS_ID")
+    @GeneratedValue(strategy = GenerationType.SEQUENCE)
+    private long id;
+    @Basic
+    private String city;
+    @Basic
+    private String country;
+    @Basic
+    private String province;
+    @Basic
+    @Column(name = "P_CODE")
+    private String postalCode;
+    @Basic
+    private String street;
+
+    public Address() {
+    }
+
+    public long getId() {
+        return this.id;
+    }
+
+    public void setId(long addressId) {
+        this.id = addressId;
+    }
+
+    public String getCity() {
+        return city;
+    }
+
+    public void setCity(String city) {
+        this.city = city;
+    }
+
+    public String getCountry() {
+        return country;
+    }
+
+    public void setCountry(String country) {
+        this.country = country;
+    }
+
+    public String getProvince() {
+        return province;
+    }
+
+    public void setProvince(String province) {
+        this.province = province;
+    }
+
+    public String getPostalCode() {
+        return this.postalCode;
+    }
+
+    public void setPostalCode(String postalCode) {
+        this.postalCode = postalCode;
+    }
+
+    public String getStreet() {
+        return street;
+    }
+
+    public void setStreet(String street) {
+        this.street = street;
+    }
+}
diff --git a/batch-fetch/src/model/Degree.java b/batch-fetch/src/model/Degree.java
new file mode 100644
index 0000000..61815ef
--- /dev/null
+++ b/batch-fetch/src/model/Degree.java
@@ -0,0 +1,53 @@
+/*******************************************************************************
+ * Copyright (c) 1998, 2012 Oracle and/or its affiliates. All rights reserved.
+ * This program and the accompanying materials are made available under the 
+ * terms of the Eclipse Public License v1.0 and Eclipse Distribution License v. 1.0 
+ * which accompanies this distribution. 
+ * The Eclipse Public License is available at http://www.eclipse.org/legal/epl-v10.html
+ * and the Eclipse Distribution License is available at 
+ * http://www.eclipse.org/org/documents/edl-v10.php.
+ *
+ * Contributors:
+ *              James Sutherland - initial example
+ ******************************************************************************/
+package model;
+
+import java.io.Serializable;
+import javax.persistence.*;
+
+/**
+ * Represents an employee's job title.
+ */
+@Entity
+@Table(name="BF_DEGREE")
+public class Degree implements Serializable {
+    @Id
+    @Column(name = "DEGREE_ID")
+    @GeneratedValue(strategy = GenerationType.SEQUENCE)
+    private long id;
+    @Basic
+    private String name;
+
+    public Degree() {
+    }
+    
+    public Degree(String name) {
+        this.name = name;
+    }
+
+    public long getId() {
+        return this.id;
+    }
+
+    public void setId(long id) {
+        this.id = id;
+    }
+
+    public String getName() {
+        return name;
+    }
+
+    public void setName(String name) {
+        this.name = name;
+    }
+}
diff --git a/batch-fetch/src/model/EmailAddress.java b/batch-fetch/src/model/EmailAddress.java
new file mode 100644
index 0000000..a1e558a
--- /dev/null
+++ b/batch-fetch/src/model/EmailAddress.java
@@ -0,0 +1,46 @@
+/*******************************************************************************
+ * Copyright (c) 1998, 2012 Oracle and/or its affiliates. All rights reserved.
+ * This program and the accompanying materials are made available under the 
+ * terms of the Eclipse Public License v1.0 and Eclipse Distribution License v. 1.0 
+ * which accompanies this distribution. 
+ * The Eclipse Public License is available at http://www.eclipse.org/legal/epl-v10.html
+ * and the Eclipse Distribution License is available at 
+ * http://www.eclipse.org/org/documents/edl-v10.php.
+ *
+ * Contributors:
+ *              James Sutherland - initial example
+ ******************************************************************************/
+package model;
+
+import javax.persistence.Column;
+import javax.persistence.Embeddable;
+
+import org.eclipse.persistence.annotations.ChangeTracking;
+import org.eclipse.persistence.annotations.ChangeTrackingType;
+
+/**
+ * Represents the email address of an employee.
+ */
+@Embeddable
+// TODO, this is currently required to workaround an issue with weaving and ElementCollection mappings.
+@ChangeTracking(ChangeTrackingType.DEFERRED)
+public class EmailAddress {
+
+    @Column(name = "EMAIL_ADDRESS")
+    private String address;
+
+    public EmailAddress() {        
+    }
+    
+    public EmailAddress(String address) {
+        setAddress(address);
+    }
+    
+    public String getAddress() {
+        return address;
+    }
+
+    public void setAddress(String address) {
+        this.address = address;
+    }
+}
diff --git a/batch-fetch/src/model/Employee.java b/batch-fetch/src/model/Employee.java
new file mode 100644
index 0000000..31358d2
--- /dev/null
+++ b/batch-fetch/src/model/Employee.java
@@ -0,0 +1,387 @@
+/*******************************************************************************
+ * Copyright (c) 1998, 2012 Oracle and/or its affiliates. All rights reserved.
+ * This program and the accompanying materials are made available under the 
+ * terms of the Eclipse Public License v1.0 and Eclipse Distribution License v. 1.0 
+ * which accompanies this distribution. 
+ * The Eclipse Public License is available at http://www.eclipse.org/legal/epl-v10.html
+ * and the Eclipse Distribution License is available at 
+ * http://www.eclipse.org/org/documents/edl-v10.php.
+ *
+ * Contributors:
+ *              dclarke - initial JPA Employee example using XML (bug 217884)
+ *              mbraeuer - annotated version, transformation
+ ******************************************************************************/
+package model;
+
+import java.io.Serializable;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import javax.persistence.*;
+
+/**
+ * The Employee class demonstrates several JPA, JPA 2.0, and EclipseLink mapping features including:
+ * <ul>
+ * <li>Generated Id
+ * <li>Version locking
+ * <li>OneToOne relationships (dependent, and independent)
+ * <li>OneToOne relationship using JoinTable
+ * <li>ManyToMany relationship
+ * <li>OneToMany relationship (dependent, and independent)
+ * <li>Embedded relationship
+ * <li>ElementCollection relationships (Basic, and Embeddable) (JPA 2.0)
+ * <li>enums
+ * <li>OrderColumn (JPA 2.0)
+ * <li>MapKeyColumn (JPA 2.0)
+ * <li>orphanRemoval (JPA 2.0)
+ * </ul>
+ */
+@Entity
+@Table(name="BF_EMPLOYEE")
+@SecondaryTable(name = "BF_SALARY")
+@NamedQueries({
+    @NamedQuery(name="standardFindAllBySalary", query="Select e from Employee e where e.salary > :salary"),
+    
+    @NamedQuery(name="joinFetchFindAllBySalary", query="Select e from Employee e "
+        + "left join fetch e.address left join fetch e.managedEmployees "
+        + "left join fetch e.jobTitle left join fetch e.degrees "
+        + "left join fetch e.manager left join fetch e.emailAddresses "
+        + "left join fetch e.projects left join fetch e.phoneNumbers "
+        + "left join fetch e.responsibilities "
+        + "where e.salary > :salary"),
+        
+    @NamedQuery(name="batchJOINFetchFindAllBySalary", query="Select e from Employee e where e.salary > :salary",
+            hints={     @QueryHint(name="eclipselink.batch", value="e.address"),
+                        @QueryHint(name="eclipselink.batch", value="e.jobTitle"),
+                        @QueryHint(name="eclipselink.batch", value="e.manager"),
+                        @QueryHint(name="eclipselink.batch", value="e.projects"),
+                        @QueryHint(name="eclipselink.batch", value="e.responsibilities"),
+                        @QueryHint(name="eclipselink.batch", value="e.managedEmployees"),
+                        @QueryHint(name="eclipselink.batch", value="e.degrees"),
+                        @QueryHint(name="eclipselink.batch", value="e.phoneNumbers"),
+                        @QueryHint(name="eclipselink.batch", value="e.emailAddresses")}),
+                        
+    @NamedQuery(name="batchEXISTSFetchFindAllBySalary", query="Select e from Employee e where e.salary > :salary",
+            hints={     @QueryHint(name="eclipselink.batch.type", value="EXISTS"),
+                        @QueryHint(name="eclipselink.batch", value="e.address"),
+                        @QueryHint(name="eclipselink.batch", value="e.jobTitle"),
+                        @QueryHint(name="eclipselink.batch", value="e.manager"),
+                        @QueryHint(name="eclipselink.batch", value="e.projects"),
+                        @QueryHint(name="eclipselink.batch", value="e.responsibilities"),
+                        @QueryHint(name="eclipselink.batch", value="e.managedEmployees"),
+                        @QueryHint(name="eclipselink.batch", value="e.degrees"),
+                        @QueryHint(name="eclipselink.batch", value="e.phoneNumbers"),
+                        @QueryHint(name="eclipselink.batch", value="e.emailAddresses")}),
+                        
+    @NamedQuery(name="batchINFetchFindAllBySalary", query="Select e from Employee e where e.salary > :salary",
+            hints={     @QueryHint(name="eclipselink.batch.type", value="IN"),
+                        @QueryHint(name="eclipselink.batch", value="e.address"),
+                        @QueryHint(name="eclipselink.batch", value="e.jobTitle"),
+                        @QueryHint(name="eclipselink.batch", value="e.manager"),
+                        @QueryHint(name="eclipselink.batch", value="e.projects"),
+                        @QueryHint(name="eclipselink.batch", value="e.responsibilities"),
+                        @QueryHint(name="eclipselink.batch", value="e.managedEmployees"),
+                        @QueryHint(name="eclipselink.batch", value="e.degrees"),
+                        @QueryHint(name="eclipselink.batch", value="e.phoneNumbers"),
+                        @QueryHint(name="eclipselink.batch", value="e.emailAddresses")}),
+
+    @NamedQuery(name="simpleJoinFetchFindAllBySalary", query="Select e from Employee e "
+        + "left join fetch e.address left join fetch e.phoneNumbers "
+        + "where e.salary > :salary"),
+        
+    @NamedQuery(name="simpleBatchJOINFetchFindAllBySalary", query="Select e from Employee e where e.salary > :salary",
+            hints={     @QueryHint(name="eclipselink.batch.type", value="JOIN"),
+                        @QueryHint(name="eclipselink.batch", value="e.address"),
+                        @QueryHint(name="eclipselink.batch", value="e.phoneNumbers")}),
+        
+    @NamedQuery(name="simpleBatchEXISTSFetchFindAllBySalary", query="Select e from Employee e where e.salary > :salary",
+            hints={     @QueryHint(name="eclipselink.batch.type", value="EXISTS"),
+                        @QueryHint(name="eclipselink.batch", value="e.address"),
+                        @QueryHint(name="eclipselink.batch", value="e.phoneNumbers")}),
+                        
+    @NamedQuery(name="simpleBatchINFetchFindAllBySalary", query="Select e from Employee e where e.salary > :salary",
+            hints={     @QueryHint(name="eclipselink.batch.type", value="IN"),
+                        @QueryHint(name="eclipselink.batch", value="e.address"),
+                        @QueryHint(name="eclipselink.batch", value="e.phoneNumbers")})
+})
+public class Employee implements Serializable {    
+    @Id
+    @Column(name = "EMP_ID")
+    @GeneratedValue(strategy = GenerationType.SEQUENCE)
+    private long id;
+    
+    @Version
+    private long version;
+
+    @Column(name = "F_NAME")
+    private String firstName;
+
+    @Column(name = "L_NAME")
+    private String lastName;
+
+    @Basic
+    @Column(name = "GENDER")
+    @Enumerated(EnumType.STRING)
+    private Gender gender = Gender.Male;
+
+    @Column(table = "BF_SALARY")
+    private double salary;
+
+    @Embedded
+    @AttributeOverrides( {
+        @AttributeOverride(name = "startDate", column = @Column(name = "START_DATE")),
+        @AttributeOverride(name = "endDate", column = @Column(name = "END_DATE")) })
+    private EmploymentPeriod period;
+
+    @OneToOne(cascade = CascadeType.ALL, orphanRemoval = true, fetch = FetchType.LAZY)
+    @JoinColumn(name = "ADDR_ID")
+    private Address address;
+    
+    @ManyToOne(fetch = FetchType.LAZY)
+    @JoinTable(name = "BF_EMP_JOB", joinColumns = @JoinColumn(name = "EMP_ID"), inverseJoinColumns = @JoinColumn(name = "TITLE_ID"))
+    private JobTitle jobTitle;
+
+    @ManyToOne(fetch = FetchType.LAZY)
+    @JoinColumn(name = "MANAGER_ID")
+    private Employee manager;
+
+    @OneToMany(mappedBy = "manager")
+    private List<Employee> managedEmployees = new ArrayList<Employee>();
+
+    @OneToMany(mappedBy = "owner", cascade = CascadeType.ALL, orphanRemoval = true)
+    private List<PhoneNumber> phoneNumbers = new ArrayList<PhoneNumber>();
+
+    @OneToMany(cascade = CascadeType.ALL, orphanRemoval = true)
+    @JoinColumn(name="EMP_ID")
+    private List<Degree> degrees = new ArrayList<Degree>();
+
+    @ManyToMany
+    @JoinTable(name = "BF_PROJ_EMP", joinColumns = @JoinColumn(name = "EMP_ID"), inverseJoinColumns = @JoinColumn(name = "PROJ_ID"))
+    private List<Project> projects = new ArrayList<Project>();
+
+    @ElementCollection
+    @CollectionTable(name = "BF_RESPONS", joinColumns = @JoinColumn(name = "EMP_ID"))
+    @Column(name = "RESPONSIBILITY")
+    @OrderColumn(name = "PRIORITY")
+    private List<String> responsibilities = new ArrayList<String>();
+
+    @ElementCollection
+    @CollectionTable(name = "BF_EMAIL", joinColumns = @JoinColumn(name = "EMP_ID"))
+    @Column(name = "EMAIL_ADDRESS")
+    @MapKeyColumn(name = "EMAIL_TYPE")
+    private Map<String, EmailAddress> emailAddresses = new HashMap<String, EmailAddress>();
+
+    public Employee() {
+    }
+
+    public long getId() {
+        return id;
+    }
+
+    public void setId(long empId) {
+        this.id = empId;
+    }
+
+    public String getFirstName() {
+        return firstName;
+    }
+
+    public void setFirstName(String fName) {
+        this.firstName = fName;
+    }
+
+    public Gender getGender() {
+        return this.gender;
+    }
+
+    public void setGender(Gender gender) {
+        this.gender = gender;
+    }
+
+    public String getLastName() {
+        return lastName;
+    }
+
+    public void setLastName(String lName) {
+        this.lastName = lName;
+    }
+
+    public long getVersion() {
+        return version;
+    }
+
+    public void setVersion(long version) {
+        this.version = version;
+    }
+    
+    public List<Degree> getDegrees() {
+        return degrees;
+    }
+
+    public void setDegrees(List<Degree> degrees) {
+        this.degrees = degrees;
+    }
+
+    public Degree addDegree(String degree) {
+        return addDegree(new Degree(degree));
+    }
+
+    public Degree addDegree(Degree degree) {
+        getDegrees().add(degree);
+        return degree;
+    }
+
+    public Degree removeDegree(Degree degree) {
+        getDegrees().remove(degree);
+        return degree;
+    }
+
+    public List<Project> getProjects() {
+        return projects;
+    }
+
+    public void setProjects(List<Project> projectList) {
+        this.projects = projectList;
+    }
+
+    public Project addProject(Project project) {
+        getProjects().add(project);
+        return project;
+    }
+
+    public Project removeProject(Project project) {
+        getProjects().remove(project);
+        return project;
+    }
+
+    public Employee getManager() {
+        return manager;
+    }
+
+    public void setManager(Employee employee) {
+        this.manager = employee;
+    }
+
+    public List<Employee> getManagedEmployees() {
+        return this.managedEmployees;
+    }
+
+    public void setManagedEmployees(List<Employee> employeeList) {
+        this.managedEmployees = employeeList;
+    }
+
+    public Employee addManagedEmployee(Employee employee) {
+        getManagedEmployees().add(employee);
+        employee.setManager(this);
+        return employee;
+    }
+
+    public Employee removeManagedEmployee(Employee employee) {
+        getManagedEmployees().remove(employee);
+        employee.setManager(null);
+        return employee;
+    }
+
+    public List<PhoneNumber> getPhoneNumbers() {
+        return phoneNumbers;
+    }
+
+    public void setPhoneNumbers(List<PhoneNumber> phoneNumberList) {
+        this.phoneNumbers = phoneNumberList;
+    }
+
+    public PhoneNumber addPhoneNumber(PhoneNumber phoneNumber) {
+        getPhoneNumbers().add(phoneNumber);
+        phoneNumber.setOwner(this);
+        return phoneNumber;
+    }
+
+    public PhoneNumber addPhoneNumber(String type, String areaCode, String number) {
+        PhoneNumber phoneNumber = new PhoneNumber(type, areaCode, number);
+        return addPhoneNumber(phoneNumber);
+    }
+
+    public PhoneNumber removePhoneNumber(PhoneNumber phoneNumber) {
+        getPhoneNumbers().remove(phoneNumber);
+        phoneNumber.setOwner(null);
+        return phoneNumber;
+    }
+
+    public void setAddress(Address address) {
+        this.address = address;
+    }
+
+    public Address getAddress() {
+        return address;
+    }
+
+    public void setPeriod(EmploymentPeriod period) {
+        this.period = period;
+    }
+
+    public EmploymentPeriod getPeriod() {
+        return period;
+    }
+
+    public double getSalary() {
+        return salary;
+    }
+
+    public void setSalary(double salary) {
+        this.salary = salary;
+    }
+
+    public List<String> getResponsibilities() {
+        return this.responsibilities;
+    }
+
+    public void setResponsibilities(List<String> responsibilities) {
+        this.responsibilities = responsibilities;
+    }
+
+    public void addResponsibility(String responsibility) {
+        getResponsibilities().add(responsibility);
+    }
+
+    public void removeResponsibility(String responsibility) {
+        getResponsibilities().remove(responsibility);
+    }
+    
+    public Map<String, EmailAddress> getEmailAddresses() {
+        return emailAddresses;
+    }
+
+    public void setEmailAddresses(Map<String, EmailAddress> emailAddresses) {
+        this.emailAddresses = emailAddresses;
+    }
+
+    public EmailAddress addEmailAddress(String type, String address) {
+        return addEmailAddress(type, new EmailAddress(address));
+    }
+
+    public EmailAddress addEmailAddress(String type, EmailAddress address) {
+        return getEmailAddresses().put(type, address);
+    }
+
+    public EmailAddress removeEmailAddress(String type) {
+        return getEmailAddresses().remove(type);
+    }
+
+    public EmailAddress getEmailAddress(String type) {
+        return getEmailAddresses().get(type);
+    }
+    
+    public JobTitle getJobTitle() {
+        return jobTitle;
+    }
+
+    public void setJobTitle(JobTitle jobTitle) {
+        this.jobTitle = jobTitle;
+    }
+
+    public String toString() {
+        return "Employee(" + getId() + ": " + getLastName() + ", " + getFirstName() + ")";
+    }
+}
diff --git a/batch-fetch/src/model/EmploymentPeriod.java b/batch-fetch/src/model/EmploymentPeriod.java
new file mode 100644
index 0000000..71a8da9
--- /dev/null
+++ b/batch-fetch/src/model/EmploymentPeriod.java
@@ -0,0 +1,63 @@
+/*******************************************************************************
+ * Copyright (c) 1998, 2012 Oracle and/or its affiliates. All rights reserved.
+ * This program and the accompanying materials are made available under the 
+ * terms of the Eclipse Public License v1.0 and Eclipse Distribution License v. 1.0 
+ * which accompanies this distribution. 
+ * The Eclipse Public License is available at http://www.eclipse.org/legal/epl-v10.html
+ * and the Eclipse Distribution License is available at 
+ * http://www.eclipse.org/org/documents/edl-v10.php.
+ *
+ * Contributors:
+ *              dclarke - initial JPA Employee example using XML (bug 217884)
+ *              mbraeuer - annotated version
+ ******************************************************************************/
+package model;
+
+import java.util.Calendar;
+
+import javax.persistence.Embeddable;
+import javax.persistence.Temporal;
+import javax.persistence.TemporalType;
+
+/**
+ * Represents the period of time an employee has worked for the company. A null
+ * endDate indicates that the employee is current.
+ * 
+ * @author djclarke
+ */
+@Embeddable
+public class EmploymentPeriod {
+
+    @Temporal(TemporalType.DATE)
+    private Calendar startDate;
+    @Temporal(TemporalType.DATE)
+    private Calendar endDate;
+
+    public Calendar getStartDate() {
+        return startDate;
+    }
+
+    public void setStartDate(Calendar startDate) {
+        this.startDate = startDate;
+    }
+
+    public void setStartDate(int year, int month, int day) {
+        Calendar date = Calendar.getInstance();
+        date.set(year, month + 1, day);
+        setStartDate(date);
+    }
+
+    public Calendar getEndDate() {
+        return endDate;
+    }
+
+    public void setEndDate(Calendar endDate) {
+        this.endDate = endDate;
+    }
+
+    public void setEndDate(int year, int month, int day) {
+        Calendar date = Calendar.getInstance();
+        date.set(year, month + 1, day);
+        setEndDate(date);
+    }
+}
diff --git a/batch-fetch/src/model/Gender.java b/batch-fetch/src/model/Gender.java
new file mode 100644
index 0000000..089ce5e
--- /dev/null
+++ b/batch-fetch/src/model/Gender.java
@@ -0,0 +1,20 @@
+/*******************************************************************************
+ * Copyright (c) 1998, 2012 Oracle and/or its affiliates. All rights reserved.
+ * This program and the accompanying materials are made available under the 
+ * terms of the Eclipse Public License v1.0 and Eclipse Distribution License v. 1.0 
+ * which accompanies this distribution. 
+ * The Eclipse Public License is available at http://www.eclipse.org/legal/epl-v10.html
+ * and the Eclipse Distribution License is available at 
+ * http://www.eclipse.org/org/documents/edl-v10.php.
+ *
+ * Contributors:
+ * 		dclarke - initial JPA Employee example using XML (bug 217884)
+ ******************************************************************************/
+package model;
+
+/**
+ * Represents an employee's gender.
+ */
+public enum Gender {
+    Female, Male
+}
diff --git a/batch-fetch/src/model/JobTitle.java b/batch-fetch/src/model/JobTitle.java
new file mode 100644
index 0000000..62c6e26
--- /dev/null
+++ b/batch-fetch/src/model/JobTitle.java
@@ -0,0 +1,53 @@
+/*******************************************************************************
+ * Copyright (c) 1998, 2012 Oracle and/or its affiliates. All rights reserved.
+ * This program and the accompanying materials are made available under the 
+ * terms of the Eclipse Public License v1.0 and Eclipse Distribution License v. 1.0 
+ * which accompanies this distribution. 
+ * The Eclipse Public License is available at http://www.eclipse.org/legal/epl-v10.html
+ * and the Eclipse Distribution License is available at 
+ * http://www.eclipse.org/org/documents/edl-v10.php.
+ *
+ * Contributors:
+ *              James Sutherland - initial example
+ ******************************************************************************/
+package model;
+
+import java.io.Serializable;
+import javax.persistence.*;
+
+/**
+ * Represents an employee's job title.
+ */
+@Entity
+@Table(name="BF_JOBTITLE")
+public class JobTitle implements Serializable {
+    @Id
+    @Column(name = "JOB_ID")
+    @GeneratedValue(strategy = GenerationType.SEQUENCE)
+    private long id;
+    @Basic
+    private String title;
+
+    public JobTitle() {
+    }
+    
+    public JobTitle(String title) {
+        this.title = title;
+    }
+
+    public long getId() {
+        return this.id;
+    }
+
+    public void setId(long id) {
+        this.id = id;
+    }
+
+    public String getTitle() {
+        return title;
+    }
+
+    public void setTitle(String title) {
+        this.title = title;
+    }
+}
diff --git a/batch-fetch/src/model/LargeProject.java b/batch-fetch/src/model/LargeProject.java
new file mode 100644
index 0000000..91aabfc
--- /dev/null
+++ b/batch-fetch/src/model/LargeProject.java
@@ -0,0 +1,52 @@
+/*******************************************************************************
+ * Copyright (c) 1998, 2012 Oracle and/or its affiliates. All rights reserved.
+ * This program and the accompanying materials are made available under the 
+ * terms of the Eclipse Public License v1.0 and Eclipse Distribution License v. 1.0 
+ * which accompanies this distribution. 
+ * The Eclipse Public License is available at http://www.eclipse.org/legal/epl-v10.html
+ * and the Eclipse Distribution License is available at 
+ * http://www.eclipse.org/org/documents/edl-v10.php.
+ *
+ * Contributors:
+ *              dclarke - initial JPA Employee example using XML (bug 217884)
+ *              mbraeuer - annotated version
+ ******************************************************************************/
+package model;
+
+import java.util.Calendar;
+
+import javax.persistence.*;
+
+/**
+ * The LargeProject class demonstrates usage of JOINED inheritance.
+ */
+@Entity
+@Table(name = "BF_LPROJECT")
+@DiscriminatorValue("L")
+public class LargeProject extends Project {
+    @Basic
+    private double budget;
+    @Basic
+    @Temporal(TemporalType.TIMESTAMP)
+    private Calendar milestone = Calendar.getInstance();
+
+    public LargeProject() {
+        super();
+    }
+
+    public double getBudget() {
+        return this.budget;
+    }
+
+    public void setBudget(double budget) {
+        this.budget = budget;
+    }
+
+    public Calendar getMilestone() {
+        return milestone;
+    }
+
+    public void setMilestone(Calendar milestone) {
+        this.milestone = milestone;
+    }
+}
diff --git a/batch-fetch/src/model/PhoneNumber.java b/batch-fetch/src/model/PhoneNumber.java
new file mode 100644
index 0000000..ea56b20
--- /dev/null
+++ b/batch-fetch/src/model/PhoneNumber.java
@@ -0,0 +1,109 @@
+/*******************************************************************************
+ * Copyright (c) 1998, 2012 Oracle and/or its affiliates. All rights reserved.
+ * This program and the accompanying materials are made available under the 
+ * terms of the Eclipse Public License v1.0 and Eclipse Distribution License v. 1.0 
+ * which accompanies this distribution. 
+ * The Eclipse Public License is available at http://www.eclipse.org/legal/epl-v10.html
+ * and the Eclipse Distribution License is available at 
+ * http://www.eclipse.org/org/documents/edl-v10.php.
+ *
+ * Contributors:
+ *              dclarke - initial JPA Employee example using XML (bug 217884)
+ *              mbraeuer - annotated version
+ ******************************************************************************/
+package model;
+
+import java.io.Serializable;
+
+import javax.persistence.*;
+
+/**
+ * Represents the phone number an employee.
+ * This demonstrates the usage of a composite Id, and Id using a ManyToOne relationship.
+ */
+@Entity
+@Table(name = "BF_PHONE")
+@IdClass(PhoneNumber.ID.class)
+public class PhoneNumber implements Serializable {
+
+    @Id
+    @Column(updatable = false)
+    private String type;
+    @Basic
+    @Column(name = "AREA_CODE")
+    private String areaCode;
+    @Basic
+    @Column(name = "P_NUMBER")
+    private String number;
+    @Id
+    @ManyToOne(fetch = FetchType.LAZY)
+    @JoinColumn(name = "EMP_ID")
+    private Employee owner;
+
+    public PhoneNumber() {
+    }
+
+    public PhoneNumber(String type, String areaCode, String number) {
+        this();
+        setType(type);
+        setAreaCode(areaCode);
+        setNumber(number);
+    }
+
+    public String getAreaCode() {
+        return areaCode;
+    }
+
+    public void setAreaCode(String areaCode) {
+        this.areaCode = areaCode;
+    }
+
+    public String getNumber() {
+        return this.number;
+    }
+
+    public void setNumber(String pNumber) {
+        this.number = pNumber;
+    }
+
+    public String getType() {
+        return type;
+    }
+
+    public void setType(String type) {
+        this.type = type;
+    }
+
+    public Employee getOwner() {
+        return this.owner;
+    }
+
+    protected void setOwner(Employee employee) {
+        this.owner = employee;
+    }
+
+    public static class ID implements Serializable {
+        public long owner;
+        public String type;
+
+        public ID() {
+        }
+
+        public ID(int empId, String type) {
+            this.owner = empId;
+            this.type = type;
+        }
+
+        public boolean equals(Object other) {
+            if (other instanceof ID) {
+                final ID otherID = (ID) other;
+                return otherID.owner == this.owner && otherID.type.equals(type);
+            }
+            return false;
+        }
+
+        public int hashCode() {
+            return (int)this.owner + this.type.hashCode();
+        }
+    }
+}
diff --git a/batch-fetch/src/model/Project.java b/batch-fetch/src/model/Project.java
new file mode 100644
index 0000000..9144fdf
--- /dev/null
+++ b/batch-fetch/src/model/Project.java
@@ -0,0 +1,87 @@
+/*******************************************************************************
+ * Copyright (c) 1998, 2012 Oracle and/or its affiliates. All rights reserved.
+ * This program and the accompanying materials are made available under the 
+ * terms of the Eclipse Public License v1.0 and Eclipse Distribution License v. 1.0 
+ * which accompanies this distribution. 
+ * The Eclipse Public License is available at http://www.eclipse.org/legal/epl-v10.html
+ * and the Eclipse Distribution License is available at 
+ * http://www.eclipse.org/org/documents/edl-v10.php.
+ *
+ * Contributors:
+ *              dclarke - initial JPA Employee example using XML (bug 217884)
+ *              mbraeuer - annotated version
+ ******************************************************************************/
+package model;
+
+import java.io.Serializable;
+
+import javax.persistence.*;
+
+/**
+ * This class represent a project that a group of employees work on.
+ * This demonstrates JOINED inheritance.
+ */
+@Entity
+@Table(name="BF_PROJECT")
+@Inheritance(strategy = InheritanceType.JOINED)
+@DiscriminatorColumn(name = "PROJ_TYPE")
+public abstract class Project implements Serializable {
+    @Id
+    @Column(name = "PROJ_ID")
+    @GeneratedValue(strategy = GenerationType.SEQUENCE)
+    private int id;
+    @Basic
+    @Column(name = "PROJ_NAME")
+    private String name;
+    @Basic
+    @Column(name = "DESCRIP")
+    private String description;
+    @Version
+    private long version;
+    @ManyToOne(fetch = FetchType.LAZY)
+    @JoinColumn(name = "LEADER_ID")
+    private Employee teamLeader;
+
+    public Project() {
+    }
+
+    public String getDescription() {
+        return this.description;
+    }
+
+    public void setDescription(String descrip) {
+        this.description = descrip;
+    }
+
+    public int getId() {
+        return this.id;
+    }
+
+    public void setId(int projId) {
+        this.id = projId;
+    }
+
+    public String getName() {
+        return this.name;
+    }
+
+    public void setName(String projName) {
+        this.name = projName;
+    }
+
+    public long getVersion() {
+        return version;
+    }
+
+    public void setVersion(long version) {
+        this.version = version;
+    }
+
+    public Employee getTeamLeader() {
+        return this.teamLeader;
+    }
+
+    public void setTeamLeader(Employee employee) {
+        this.teamLeader = employee;
+    }
+}
diff --git a/batch-fetch/src/model/SmallProject.java b/batch-fetch/src/model/SmallProject.java
new file mode 100644
index 0000000..41d0470
--- /dev/null
+++ b/batch-fetch/src/model/SmallProject.java
@@ -0,0 +1,38 @@
+/*******************************************************************************
+ * Copyright (c) 1998, 2012 Oracle and/or its affiliates. All rights reserved.
+ * This program and the accompanying materials are made available under the 
+ * terms of the Eclipse Public License v1.0 and Eclipse Distribution License v. 1.0 
+ * which accompanies this distribution. 
+ * The Eclipse Public License is available at http://www.eclipse.org/legal/epl-v10.html
+ * and the Eclipse Distribution License is available at 
+ * http://www.eclipse.org/org/documents/edl-v10.php.
+ *
+ * Contributors:
+ *              dclarke - initial JPA Employee example using XML (bug 217884)
+ *              mbraeuer - annotated version
+ ******************************************************************************/
+package model;
+
+import javax.persistence.*;
+
+/**
+ * The SmallProject class demonstrates usage of a way to limit a subclass to its parent's table when JOINED
+ * inheritance is used.  This avoids having to have an empty SMALLPROJECT table by setting the table to that
+ * of the superclass.
+ */
+@Entity
+@Table(name = "BF_PROJECT")
+@DiscriminatorValue("S")
+public class SmallProject extends Project {
+
+	private SmallProject() {
+		super();
+	}
+
+	public SmallProject(String name, String description) {
+		this();
+		setName(name);
+		setDescription(description);
+	}
+
+}
diff --git a/database-partitioning/.classpath b/database-partitioning/.classpath
new file mode 100644
index 0000000..4e2db7c
--- /dev/null
+++ b/database-partitioning/.classpath
@@ -0,0 +1,12 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<classpath>
+	<classpathentry kind="src" path="src"/>
+	<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER"/>
+	<classpathentry kind="con" path="org.eclipse.jdt.USER_LIBRARY/EclipseLink 1.2">
+		<attributes>
+			<attribute name="owner.project.facets" value="jpt.jpa;#system#"/>
+		</attributes>
+	</classpathentry>
+	<classpathentry kind="con" path="org.eclipse.jdt.USER_LIBRARY/Oracle JDBC"/>
+	<classpathentry kind="output" path="classes"/>
+</classpath>
diff --git a/database-partitioning/.project b/database-partitioning/.project
new file mode 100644
index 0000000..65bd5ef
--- /dev/null
+++ b/database-partitioning/.project
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<projectDescription>
+	<name>org.eclipse.persistence.example.jpa.partitioned</name>
+	<comment></comment>
+	<projects>
+	</projects>
+	<buildSpec>
+		<buildCommand>
+			<name>org.eclipse.jdt.core.javabuilder</name>
+			<arguments>
+			</arguments>
+		</buildCommand>
+		<buildCommand>
+			<name>org.eclipse.wst.common.project.facet.core.builder</name>
+			<arguments>
+			</arguments>
+		</buildCommand>
+		<buildCommand>
+			<name>org.eclipse.wst.validation.validationbuilder</name>
+			<arguments>
+			</arguments>
+		</buildCommand>
+	</buildSpec>
+	<natures>
+		<nature>org.eclipse.wst.common.project.facet.core.nature</nature>
+		<nature>org.eclipse.jdt.core.javanature</nature>
+		<nature>org.eclipse.wst.common.modulecore.ModuleCoreNature</nature>
+		<nature>org.eclipse.jem.workbench.JavaEMFNature</nature>
+	</natures>
+</projectDescription>
diff --git a/database-partitioning/build.xml b/database-partitioning/build.xml
new file mode 100644
index 0000000..fca54d2
--- /dev/null
+++ b/database-partitioning/build.xml
@@ -0,0 +1,40 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project basedir="." default="build" name="org.eclipse.persistence.example.jpa.partitioned">
+    <property environment="env"/>
+    <property name="JDBC_LIB" value="./mysql-connector-java-5.0.7-bin.jar"/>
+    <property name="JPA_LIB" value="./persistence.jar"/>
+    <property name="ECLIPSELINK_LIB" value="./eclipselink.jar"/>
+    <property name="AGENT" value="-javaagent:${ECLIPSELINK_LIB}"/>
+    <property name="debuglevel" value="source,lines,vars"/>
+    <path id="example.classpath">
+        <pathelement location="classes"/>
+        <pathelement location="${JDBC_LIB}"/>
+        <pathelement location="${JPA_LIB}"/>
+        <pathelement location="${ECLIPSELINK_LIB}"/>
+    </path>
+    <target name="init" depends="clean">
+        <mkdir dir="classes"/>
+    </target>
+    <target name="clean">
+        <delete dir="classes"/>
+    </target>
+
+    <target depends="init" name="build">
+        <echo message="${ant.project.name}: ${ant.file}"/>
+        <javac debug="true" debuglevel="${debuglevel}" destdir="classes">
+            <src path="src"/>
+            <exclude name="**/.svn/**"/>
+            <classpath refid="example.classpath"/>
+        </javac>
+        <copy file="src/META-INF/persistence.xml" todir="classes/META-INF"/>
+    </target>
+
+    <target name="test" depends="build">
+        <java classname="example.Test"
+                maxmemory="512m"
+                fork="true">
+               <jvmarg value="${AGENT}"/>
+            <classpath refid="example.classpath"/>
+        </java>
+    </target>
+</project>
diff --git a/database-partitioning/database-partitioning.zip b/database-partitioning/database-partitioning.zip
new file mode 100644
index 0000000..ac4a741
--- /dev/null
+++ b/database-partitioning/database-partitioning.zip
Binary files differ
diff --git a/database-partitioning/src/META-INF/persistence.xml b/database-partitioning/src/META-INF/persistence.xml
new file mode 100644
index 0000000..757f054
--- /dev/null
+++ b/database-partitioning/src/META-INF/persistence.xml
@@ -0,0 +1,61 @@
+<?xml version="1.0" encoding="UTF-8" ?>
+<persistence xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+        xsi:schemaLocation="http://java.sun.com/xml/ns/persistence http://java.sun.com/xml/ns/persistence/persistence_2_0.xsd"
+        version="2.0" xmlns="http://java.sun.com/xml/ns/persistence">
+    <persistence-unit name="order" transaction-type="RESOURCE_LOCAL">
+        <class>model.Order</class>
+        <class>model.OrderLine</class>
+        <class>model.Customer</class>
+        <properties>
+            <!-- Default database login using MySQL for EclipseLink's internal connection pool,
+                 change this to access your own database. -->
+            <property name="javax.persistence.jdbc.driver" value="com.mysql.jdbc.Driver" />
+            <property name="javax.persistence.jdbc.url" value="jdbc:mysql://node1:3306/mysql" />
+            <property name="javax.persistence.jdbc.user" value="root" />
+            <property name="javax.persistence.jdbc.password" value="password" />
+
+            <!-- The database platform is auto-detected by default,
+                 if you want to set a specific platform this can be set. -->
+            <!-- property name=""eclipselink.target-database" value="Oracle" / -->
+
+            <!-- Configure connection pool. -->
+            <property name="eclipselink.connection-pool.default.initial" value="1" />
+            <property name="eclipselink.connection-pool.default.min" value="64" />
+            <property name="eclipselink.connection-pool.default.max" value="64" />
+            
+            <!-- Configure 2nd database connection pool. -->
+            <property name="eclipselink.connection-pool.node2.url" value="jdbc:mysql://node2:3306/mysql" />
+            <property name="eclipselink.connection-pool.node2.user" value="root" />
+            <property name="eclipselink.connection-pool.node2.password" value="password" />
+            <property name="eclipselink.connection-pool.node2.initial" value="1" />
+            <property name="eclipselink.connection-pool.node2.min" value="64" />
+            <property name="eclipselink.connection-pool.node2.max" value="64" />
+            
+            <!-- Default partioning to replication to allow DDL to be sent to all nodes -->
+            <property name="eclipselink.partitioning" value="Replicate" />
+            
+            <!-- Enabled statement caching, this is only required when using internal connection pooling,
+                 when using a DataSource, statement caching must be configured in the DataSource. -->
+            <property name="eclipselink.jdbc.cache-statements" value="true" />
+
+            <!-- In JSE no server platform is used, if you wish to use this example is a JEE server with JTA,
+                             then you need to set this. -->
+            <!-- property name="eclipselink.target-server" value="WebLogic" / -->
+
+            <!-- Caching is disabled for this example to stress the database more. -->
+            <property name="eclipselink.cache.shared.default" value="false" />
+
+            <!-- If desired, this option would force a JDBC connection to be held for the duration of an EntityManager,
+                 instead of returned to the pool in between queries/transactions. -->
+            <!-- property name="eclipselink.jdbc.exclusive-connection.mode" value="Always" / -->
+
+            <!-- Configure database to be created on startup if not already existing. -->
+            <!-- property name="eclipselink.ddl-generation" value="create-tables" / -->
+            <!-- To drop and replace existing schema this can be used. -->
+            <!-- property name="eclipselink.ddl-generation" value="drop-and-create-tables" / -->
+
+            <!-- Configure logging for demonstration. -->
+            <!-- property name="eclipselink.logging.level" value="FINE" / -->
+        </properties>
+    </persistence-unit>
+</persistence>
diff --git a/database-partitioning/src/example/Test.java b/database-partitioning/src/example/Test.java
new file mode 100644
index 0000000..d5a3438
--- /dev/null
+++ b/database-partitioning/src/example/Test.java
@@ -0,0 +1,222 @@
+/*******************************************************************************
+ * Copyright (c) 1998, 2012 Oracle and/or its affiliates. All rights reserved.
+ * This program and the accompanying materials are made available under the 
+ * terms of the Eclipse Public License v1.0 and Eclipse Distribution License v. 1.0 
+ * which accompanies this distribution. 
+ * The Eclipse Public License is available at http://www.eclipse.org/legal/epl-v10.html
+ * and the Eclipse Distribution License is available at 
+ * http://www.eclipse.org/org/documents/edl-v10.php.
+ *
+ * Contributors:
+ *      Oracle - initial impl
+ ******************************************************************************/
+package example;
+
+import java.math.BigDecimal;
+import java.util.ArrayList;
+import java.util.List;
+
+import javax.persistence.EntityManager;
+import javax.persistence.EntityManagerFactory;
+import javax.persistence.Persistence;
+
+import model.*;
+
+/**
+ * Simulates a large load of order processing.
+ * @author James Sutherland
+ */
+public class Test {
+
+    public static int REPEATS = 5;
+    public static int THREADS = 16;
+    public static int RUN_TIME = 600;//60000; //1 minute.
+
+    protected static volatile int executions;
+    
+    /**
+     * Measure the performance of the run.
+     * Repeat the run REPEATS (5) times,
+     * and measure the number of execution in RUN_TIME (60s).
+     */
+    public static void executeRun(String name, final Runnable runnable) {
+        System.out.println("Starting run: " + name);
+        
+        List<Integer> results = new ArrayList<Integer>();
+        // Repeat the test and baseline for the number of repeats.
+        for (int repeat = 0; repeat < REPEATS; repeat++) {
+            System.gc();
+            try {
+                Thread.sleep(1000);
+            } catch (InterruptedException ignore) {}
+            executions = 0;
+            Thread[] threads = new Thread[THREADS];
+            for (int thread = 0; thread < THREADS; thread++) {
+                Runnable worker = new Runnable() {
+                    public void run() {
+                        long startTime, endTime;
+                        startTime = System.currentTimeMillis();
+                        endTime = startTime;
+                        // Count how many times the test can be invoked in the run time.
+                        // This allows for the test run time to be easily changed.
+                        while ((startTime + RUN_TIME) >= endTime) {
+                            runnable.run();
+                            executions++;
+                            endTime = System.currentTimeMillis();
+                        }
+                    }
+                };
+                threads[thread] = new Thread(worker);                
+            }
+            for (Thread thread : threads) {
+                thread.start();
+            }
+            for (Thread thread : threads) {
+                try {
+                    thread.join();
+                } catch (InterruptedException ignore) {}
+            }
+            results.add(executions);
+            System.out.println("Done run: " +  repeat + " for: " + name);
+        }
+        
+        System.out.println("Completed run: " + name);
+
+        System.out.println("");
+        System.out.println(name + " Results");
+        System.out.println("Run repeats:" + REPEATS);
+        System.out.println("Run threads:" + THREADS);
+        System.out.println("Run time:" + RUN_TIME + "ms");
+        System.out.println("Average result:" + averageResults(results));
+        System.out.println("Max result:" + maxResults(results));
+        System.out.println("Min result:" + minResults(results));
+        System.out.println("% standard deviation:" + standardDeviationResults(results));
+        System.out.println("");
+        System.out.println("");        
+    }
+
+    /**
+     * Compute the max of the results.
+     */
+    public static int maxResults(List<Integer> times) {
+        int testMax = 0;
+        for (int index = 0; index < times.size(); index++) {
+            int time = times.get(index);
+            if (time > testMax) {
+                testMax = time;
+            }
+        }
+        return testMax;
+    }
+
+    /**
+     * Compute the min of the results.
+     */
+    public static int minResults(List<Integer> times) {
+        int testMin = 0;
+        for (int index = 0; index < times.size(); index++) {
+            int time = times.get(index);
+            if ((testMin == 0) || (time < testMin)) {
+                testMin = time;
+            }
+        }
+        return testMin;
+    }
+
+    /**
+     * Filter max and min from results.
+     */
+    public static List<Integer> filterMaxMinResults(List<Integer> times) {
+        List filteredTimes = new ArrayList(times);
+        if (filteredTimes.size() > 3) {
+            filteredTimes.remove((Integer)maxResults(times));
+            filteredTimes.remove((Integer)minResults(times));
+        }
+        return filteredTimes;
+    }
+
+    /**
+     * Compute the average of the results rejecting the min and max.
+     */
+    public static double averageResults(List<Integer> allTimes) {
+        // Compute the average reject the min and max to improve consistency.
+        List<Integer> times = filterMaxMinResults(allTimes);
+        double testAverage = 0;
+        for (int index = 0; index < times.size(); index++) {
+            int time = times.get(index);
+            testAverage = testAverage + time;
+        }
+        testAverage = testAverage / times.size();
+        return testAverage;
+    }
+
+    /**
+     * Compute the standard deviation of the results rejecting the min and max.
+     */
+    public static double standardDeviationResults(List<Integer> allTimes) {
+        // Compute the average reject the min and max to improve consistency.
+        double testAverage = averageResults(allTimes);
+
+        // Compute the standard deviation reject the min and max to improve consistency.
+        List<Integer> times = filterMaxMinResults(allTimes);
+        double testStandardDeviation = 0;
+        for (int index = 0; index < times.size(); index++) {
+            int time = times.get(index);
+            testStandardDeviation = testStandardDeviation + Math.pow(time - testAverage, 2);
+        }
+        testStandardDeviation = testStandardDeviation / times.size();
+        testStandardDeviation = Math.sqrt(testStandardDeviation);
+        // As percent of average
+        testStandardDeviation = (testStandardDeviation / testAverage) * 100;
+        return testStandardDeviation;
+    }
+
+
+    public static void main(String[] args) throws Exception {
+        final EntityManagerFactory emf = Persistence.createEntityManagerFactory("order");
+        EntityManager em = emf.createEntityManager();
+        // Drop constraint to allow cross partition relationship.
+        em.getTransaction().begin();
+        em.createNativeQuery("ALTER TABLE PART_ORDER DROP FOREIGN KEY FK_PART_ORDER_CUSTOMER_ID").executeUpdate();
+        em.getTransaction().commit();
+        em.close();
+        executeRun("place-orders", new Runnable() {
+            ThreadLocal<Customer> customer = new ThreadLocal<Customer>();
+            public void run() {
+                Test test = new Test();
+                if (customer.get() == null) {
+                    customer.set(test.createCustomer(emf));
+                }
+                test.placeOrder(customer.get(), emf);
+            }
+        });
+        emf.close();
+    }
+
+    public Customer createCustomer(EntityManagerFactory emf) {        
+        EntityManager em = emf.createEntityManager();
+        Customer customer = new Customer();
+        customer.setName("AMCE-" + System.currentTimeMillis());
+        em.getTransaction().begin();
+        em.persist(customer);
+        em.getTransaction().commit();
+        em.close();
+        return customer;
+    }
+
+    public Order placeOrder(Customer customer, EntityManagerFactory emf) {        
+        EntityManager em = emf.createEntityManager();
+        customer = em.find(customer.getClass(), customer.getId());
+        Order order = new Order();
+        order.setDescription("Order-" + System.currentTimeMillis());
+        for (int index = 0; index<10; index++) {
+            order.addOrderLine(new OrderLine("item-" + index, new BigDecimal(index * 100)));
+        }
+        customer.addOrder(order);
+        em.getTransaction().begin();
+        em.persist(order);
+        em.getTransaction().commit();
+        em.close();
+        return order;
+    }
+}
diff --git a/database-partitioning/src/model/Customer.java b/database-partitioning/src/model/Customer.java
new file mode 100644
index 0000000..ce46b37
--- /dev/null
+++ b/database-partitioning/src/model/Customer.java
@@ -0,0 +1,74 @@
+/*******************************************************************************
+ * Copyright (c) 2011, 2012 Oracle and/or its affiliates. All rights reserved.
+ * This program and the accompanying materials are made available under the 
+ * terms of the Eclipse Public License v1.0 and Eclipse Distribution License v. 1.0 
+ * which accompanies this distribution. 
+ * The Eclipse Public License is available at http://www.eclipse.org/legal/epl-v10.html
+ * and the Eclipse Distribution License is available at 
+ * http://www.eclipse.org/org/documents/edl-v10.php.
+ *
+ * Contributors:
+ *      Oracle - initial impl
+ ******************************************************************************/
+package model;
+
+import java.io.Serializable;
+import java.util.ArrayList;
+import java.util.List;
+
+import javax.persistence.*;
+
+import org.eclipse.persistence.annotations.HashPartitioning;
+import org.eclipse.persistence.annotations.Partitioned;
+import org.eclipse.persistence.annotations.ReplicationPartitioning;
+
+/**
+ * Customer, hash partitioned by Id.
+ * @author James Sutherland
+ */
+@Entity
+@Table(name="PART_CUSTOMER")
+@ReplicationPartitioning(name="Replicate", connectionPools={"default","node2"})
+@HashPartitioning(name="HashPartitionById", partitionColumn=@Column(name="ID"), connectionPools={"default","node2"})
+@Partitioned("HashPartitionById")
+public class Customer implements Serializable {
+    @Id
+    @GeneratedValue(strategy=GenerationType.TABLE)
+    private long id;
+    @Basic
+    private String name;
+    @OneToMany(mappedBy="customer")
+    private List<Order> orders = new ArrayList<Order>();
+
+    public Customer() {
+    }
+
+    public long getId() {
+        return id;
+    }
+
+    public void setId(long id) {
+        this.id = id;
+    }
+
+    public String getName() {
+        return name;
+    }
+
+    public void setName(String name) {
+        this.name = name;
+    }
+
+    public List<Order> getOrders() {
+        return orders;
+    }
+
+    public void setOrders(List<Order> orders) {
+        this.orders = orders;
+    }
+    
+    public void addOrder(Order order) {
+        order.setCustomer(this);
+        getOrders().add(order);
+    }
+}
diff --git a/database-partitioning/src/model/Order.java b/database-partitioning/src/model/Order.java
new file mode 100644
index 0000000..12d36d0
--- /dev/null
+++ b/database-partitioning/src/model/Order.java
@@ -0,0 +1,100 @@
+/*******************************************************************************
+ * Copyright (c) 1998, 2012 Oracle and/or its affiliates. All rights reserved.
+ * This program and the accompanying materials are made available under the 
+ * terms of the Eclipse Public License v1.0 and Eclipse Distribution License v. 1.0 
+ * which accompanies this distribution. 
+ * The Eclipse Public License is available at http://www.eclipse.org/legal/epl-v10.html
+ * and the Eclipse Distribution License is available at 
+ * http://www.eclipse.org/org/documents/edl-v10.php.
+ *
+ * Contributors:
+ *      Oracle - initial impl
+ ******************************************************************************/
+package model;
+
+import java.io.Serializable;
+import java.math.BigDecimal;
+import java.util.ArrayList;
+import java.util.List;
+
+import javax.persistence.*;
+
+import org.eclipse.persistence.annotations.HashPartitioning;
+import org.eclipse.persistence.annotations.Partitioned;
+
+/**
+ * Order, hash partitioned by the Order's Id.
+ * @author James Sutherland
+ */
+@Entity
+@Table(name="PART_ORDER")
+@HashPartitioning(name="HashPartitionByOrderId", partitionColumn=@Column(name="ORDER_ID"), connectionPools={"default","node2"})
+@Partitioned("HashPartitionByOrderId")
+public class Order implements Serializable {
+    @Id
+    @GeneratedValue(strategy=GenerationType.TABLE)
+    @Column(name="ORDER_ID")
+    private long id;
+    @Basic
+    private String description;
+    @Basic
+    private BigDecimal totalCost = BigDecimal.valueOf(0);
+    @OneToMany(mappedBy="order", cascade=CascadeType.ALL, orphanRemoval=true)
+    @OrderBy("lineNumber")
+    private List<OrderLine> orderLines = new ArrayList<OrderLine>();
+    @ManyToOne(fetch=FetchType.LAZY)
+    private Customer customer;
+
+    public Order() {
+    }
+
+    public long getId() {
+        return id;
+    }
+
+    public void setId(long id) {
+        this.id = id;
+    }
+
+    public String getDescription() {
+        return description;
+    }
+
+    public void setDescription(String description) {
+        this.description = description;
+    }
+
+    public BigDecimal getTotalCost() {
+        return totalCost;
+    }
+
+    public void setTotalCost(BigDecimal totalCost) {
+        this.totalCost = totalCost;
+    }
+
+    public List<OrderLine> getOrderLines() {
+        return orderLines;
+    }
+
+    public void setOrderLines(List<OrderLine> orderLines) {
+        this.orderLines = orderLines;
+    }
+
+    public Customer getCustomer() {
+        return customer;
+    }
+
+    public void setCustomer(Customer customer) {
+        this.customer = customer;
+    }
+    
+    /**
+     * Add the order line to the order, and set the back reference and update the order cost.
+     */
+    public void addOrderLine(OrderLine orderLine) {
+        orderLine.setOrder(this);
+        getOrderLines().add(orderLine);
+        orderLine.setLineNumber(getOrderLines().size());
+        setTotalCost(getTotalCost().add(orderLine.getCost()));
+    }
+}
diff --git a/database-partitioning/src/model/OrderLine.java b/database-partitioning/src/model/OrderLine.java
new file mode 100644
index 0000000..0ef8ce2
--- /dev/null
+++ b/database-partitioning/src/model/OrderLine.java
@@ -0,0 +1,81 @@
+/*******************************************************************************
+ * Copyright (c) 2011, 2012 Oracle and/or its affiliates. All rights reserved.
+ * This program and the accompanying materials are made available under the 
+ * terms of the Eclipse Public License v1.0 and Eclipse Distribution License v. 1.0 
+ * which accompanies this distribution. 
+ * The Eclipse Public License is available at http://www.eclipse.org/legal/epl-v10.html
+ * and the Eclipse Distribution License is available at 
+ * http://www.eclipse.org/org/documents/edl-v10.php.
+ *
+ * Contributors:
+ *      Oracle - initial impl
+ ******************************************************************************/
+package model;
+
+import java.io.Serializable;
+import java.math.BigDecimal;
+
+import javax.persistence.*;
+
+import org.eclipse.persistence.annotations.Partitioned;
+
+/**
+ * OrderLine, help by Order, hash partitioned by the Order's Id.
+ * @author James Sutherland
+ */
+@Entity
+@Table(name="PART_ORDERLINE")
+@Partitioned("HashPartitionByOrderId")
+public class OrderLine implements Serializable {
+    @Id
+    @ManyToOne(fetch=FetchType.LAZY)
+    @JoinColumn(name="ORDER_ID")
+    private Order order;
+    @Id
+    private int lineNumber;
+    @Basic
+    private String description;
+    @Basic
+    private BigDecimal cost = BigDecimal.valueOf(0);
+
+    public OrderLine() {
+    }
+    
+    public OrderLine(String description, BigDecimal cost) {
+        this.description = description;
+        this.cost = cost;
+    }
+
+    public Order getOrder() {
+        return order;
+    }
+
+    public void setOrder(Order order) {
+        this.order = order;
+    }
+
+    public int getLineNumber() {
+        return lineNumber;
+    }
+
+    public void setLineNumber(int lineNumber) {
+        this.lineNumber = lineNumber;
+    }
+
+    public String getDescription() {
+        return description;
+    }
+
+    public void setDescription(String description) {
+        this.description = description;
+    }
+
+    public BigDecimal getCost() {
+        return cost;
+    }
+
+    public void setCost(BigDecimal cost) {
+        this.cost = cost;
+    }
+    
+}