340 likes | 545 Views
CG0165: Advanced Applications Development in Java. Persistence in Java Enterprise Container Managed Persistence Application Managed Persistence. Michael Brockway Sajjad Shami. Northumbria University School of Computing, Engineering & Information Sciences. Persistence. Entity
E N D
CG0165: Advanced Applications Development in Java • Persistence in Java Enterprise • Container Managed Persistence • Application Managed Persistence Michael Brockway Sajjad Shami Northumbria University School of Computing, Engineering & Information Sciences
Persistence • Entity • Entity Relationships • Container-managed Entity Management • Application-managed Entity Management • Examples • References: • Tutorial and reference material on the sun web site - Enterprise Edition pages • http://java.sun.com/javaee/5/docs/tutorial/doc/ • Read chapter 20 Enterprise Beans; and chapters 24-26, on persistence. • Deitel, Deitel & Santry Advanced Java, chap 15, describes an example based on an Employee database. Their example does not work in the way they describe its deployment, in J2EE1.3, but you might like to try adapting it so that it does, once you have mastered the present material.
Java Persistence API • provides an object/relational mapping facility to Java developers • for managing relational data in Java applications • Java Persistence consists of three areas: • The Java Persistence API • The query language • Object/relational mapping metadata • the API defines the Java classes • package: javax.persistence • package: javax.persistence.spi
Entity • a lightweight persistence domain object • represents a table in a relational database • each entity instance corresponds to a row in that table • the primary programming artifact of an entity is the entity class, although entities can use helper classes • the persistent state of an entity is represented • either through persistent fields • or persistent properties
Requirements for Entity Class • must be annotated with the javax.persistence.Entity annotation • must have a public or protected, no-argument constructor • may have other constructors • must not be declared final • no methods or persistent instance variables must be declared final • if an entity instance be passed by value as a detached object, the class must implement the Serializable interface • entities may extend both entity and non-entity classes, and non-entity classes may extend entity classes • persistent instance variables must be declared private, protected, or package-private • and can only be accessed directly by the entity class’s methods • clients should access the entity’s state through accessor or business methods
Types of Fields and Properties • Java primitive types • • java.lang.String • • other serializable types including: • • wrappers of Java primitive types • • java.math.BigInteger • • java.math.BigDecimal • • java.util.Date • • java.util.Calendar • • java.sql.Date • • java.sql.Time • java.sql.TimeStamp • user-defined serializable types • byte[] • Byte[] • char[] • Character[] • enumerated types • other entities and/or collections of entities • embeddable classes
Fields and Properties • Persistent Fields • if the entity class uses persistent fields, the Persistence runtime accesses entity class instance variables directly • all fields not annotated javax.persistence.Transient will be persisted to the data store • Persistent Properties • if the entity uses persistent properties, the entity must follow the method conventions of JavaBeans components • JavaBeans-style properties use getter and setter methods that are named after the entity class’s instance variable names
Primary Key • each entity has a unique object identifier • an employee entity, for example, might be identified by an employee number • the unique identifier, or primary key, enables clients to locate a particular entity instance • every entity must have a primary key • an entity may have either a simple or a composite primary key • simple primary keys use the javax.persistence.Id annotation to denote the primary key property or field • composite primary keys are denoted using the javax.persistence.EmbeddedId and javax.persistence.IdClass annotations
Primary Key Classes • access control modifier must be public • properties must be public or protected if property-based access is used • must have a public default constructor • must implement the hashCode() and equals(Object other) methods • must be serializable • composite primary key must be represented and mapped to multiple fields or properties of the entity class • or must be represented and mapped as an embeddable class • if the class is mapped to multiple fields or properties of the entity class, the names and types of the primary key fields or properties in the primary key class must match those of the entity class
Composite Key Example • the following primary key class is a composite key • the orderId and itemId fields together uniquely identify an entity public final class LineItemKey implements Serializable { public Integer orderId; public int itemId; public LineItemKey() {} public LineItemKey(Integer orderId, int itemId) { this.orderId = orderId; sthis.itemId = itemId; } public boolean equals(Object otherOb) { if (this == otherOb) { return true; } if (!(otherOb instanceof LineItemKey)) { return false; }
Composite Key Example Contd. LineItemKey other = (LineItemKey) otherOb; return ( (orderId==null?other.orderId==null:orderId.equals (other.orderId) ) && (itemId == other.itemId) ); } public int hashCode() { return ( (orderId==null?0:orderId.hashCode()) ^ ((int) itemId) ); } public String toString() { return "" + orderId + "-" + itemId; } }
Entity Relationships_Multiplicity • four types: • One-to-one: each entity instance is related to a single instance of another entity • use the javax.persistence.OneToOne annotation on the corresponding persistent property or field • One-to-many: an entity instance can be related to multiple instances of the other entities. • use the javax.persistence.OneToMany annotation • Many-to-one: multiple instances of an entity can be related to a single instance of the other entity. • use the javax.persistence.ManyToOne annotation • Many-to-many: the entity instances can be related to multiple instances of each other • use the javax.persistence.ManyToMany annotation
Entity Relationships_Direction • can be either bidirectional or unidirectional • a bidirectional relationship has both an owning side and an inverse side • a unidirectional relationship has only an owning side • the owning side of a relationship determines how the Persistence runtime makes updates to the relationship in the database
Entity Management • entities are managed by the entity manager • the entity manager is represented by javax.persistence.EntityManager instances • each EntityManager instance is associated with a persistence context • a persistence context defines scope under which particular entity instances are created, persisted, and removed • is a set of managed entity instances that exist in a particular data store • the EntityManager interface defines the methods that are used to interact with the persistence context • the EntityManager API • creates and removes persistent entity instances • finds entities by the entity’s primary key • allows queries to be run on entities
Container Managed Entity Management • with a container-managed entity manager, an EntityManager instance’s persistence context is automatically propagated by the container • to all application components • that use the EntityManager instance within a single Java Transaction Architecture (JTA) transaction • JTA transactions usually involve calls across application components • to complete a JTA transaction, these components usually need access to a single persistence context • this occurs when an EntityManager is injected into the application components via the javax.persistence.PersistenceContext annotation
Application Managed Entity Management • with application-managed entity managers, the persistence context is not propagated to application components • and the lifecycle of EntityManager instances is managed by the application • are used when applications need to access a persistence context that is not propagated with the JTA transaction across EntityManager instances in a particular persistence unit • each EntityManager creates a new, isolated persistence context • the EntityManager, and its associated persistence context, is created and destroyed explicitly by the application • applications create EntityManager instances in this case by using the createEntityManager method of javax.persistence.EntityManagerFactory
Finding Entities • the EntityManager.find method is used to look up entities in the data store by the entity’s primary key @PersistenceContext EntityManager em; public void enterOrder(int custID, Order newOrder) { Customer cust = em.find(Customer.class, custID); cust.getOrders().add(newOrder); newOrder.setCustomer(cust); }
Entity Instance’s Life Cycle • entity instances are managed by invoking operations on the entity via an Entity-Manager instance • entity instances are in one of four states: • new • managed • detached • removed
Persisting Entity Instances • new entity instances become managed and persistent by invoking its persist method @PersistenceContext EntityManager em; ... public LineItem createLineItem(Order order, Product product, int quantity) { LineItem li = new LineItem(order, product, quantity); order.getLineItems().add(li); em.persist(li); return li; }
Removing Entity Instances • managed entity instances are removed • by invoking its remove method, • or by a cascading remove operation invoked from related entities that have the cascade= REMOVE or cascade=ALL elements set in the relationship annotation public void removeOrder(Integer orderId) { try { Order order = em.find(Order.class, orderId); em.remove(order); }...
Synchronizing to Database • the state of persistent entities is synchronized to the database when the transaction with which the entity is associated commits • if a managed entity is in a bidirectional relationship with another managed entity, the data will be persisted based on the owning side of the relationship • to force synchronization of the managed entity to the data store, invoke the flush method of the entity.
Creating Queries • the EntityManager.createQuery and EntityManager.createNamedQuery methods are used to query the datastore using Java Persistence query language queries • the createQuery method is used to create dynamic queries • defined directly within an application’s business logic • the createNamedQuery method is used to create static queries • defined in metadata using the javax.persistence.NamedQuery annotation
Persistence Unit • defines a set of all entity classes that are managed by Entity-Manager instances in an application • this set of entity classes represents the data contained within a single data store • are defined by the persistence.xml configuration file • the JAR file or directory whose META-INF directory contains persistence.xml is called the root of the persistence unit • the scope of the persistence unit is determined by the persistence unit’s root
persistence.xml • persistence.xml defines one or more persistence units • example persistence.xml file <persistence> <persistence-unit name="OrderManagement"> <description>This unit manages orders and customers. It does not rely on any vendor-specific features and can therefore be deployed to any persistence provider. </description> <jta-data-source>jdbc/MyOrderDB</jta-data-source> <jar-file>MyOrderApp.jar</jar-file> <class>com.widgets.Order</class> <class>com.widgets.Customer</class> </persistence-unit> </persistence>
Persistence in the EJB Tier • Java Persistence API can be used from enterprise beans • two examples • ‘order’ • an application that uses a stateful session bean • to manage entities related to an ordering system • ‘roster’ • an application that manages a community sports system
The order Application • is a simple inventory and ordering application for maintaining a catalog of parts and placing an itemized order of those parts • has entities that represent parts, vendors, orders, and line items. • accessed using a stateful session bean • that holds the business logic of the application • a simple commandline client adds data to the entities, manipulates the data, and displays data from the catalog • consists of two modules: • order-ejb • an enterprise bean JAR file containing the entities, the support classes, and a stateful session bean that accesses the data in the entitiess • order-app-client • the application client that populates the entities with data and manipulates the data, displaying the results in a terminal
order Application: source files • entity • LineItem.java • LineItemKey.java • Order.java • Part.java • PartKey.java • Vendor.java • VendorPart.java • request • Request.java • RequestBean.java • order-app-client • OrderClient.java
order Application: features • Entity Relationships • Self-Referential Relationships • One-to-One Relationships • One-to-Many Relationships Mapped to Overlapping Primary and Foreign Keys • Unidirectional Relationships • Primary Keys • Generated Primary Keys • Compound Primary Keys • Entities Mapped to More than One Database Table
order Application: features … contd • Cascade Operations • BLOB and CLOB Database Types • Temporal Types • Managing order’s Entities • Creating Entities • Finding Entities • Setting Entity Relationships • Using Queries • Removing Entities
order Application: build, deploy, run • Start Default Server • Start JavaDB • Start Admin Console • In console go to …../order> • >ant create-tables • >ant • >ant deploy • >ant run
order Application: output ... run: [echo] Running appclient for Order. appclient-command-common: [exec] Cost of Bill of Material for PN SDFG-ERTY-BN Rev: 7: $241.86 [exec] Cost of Order 1111: $664.68 [exec] Cost of Order 4312: $2,011.44 [exec] Adding 5% discount [exec] Cost of Order 1111: $627.75 [exec] Cost of Order 4312: $1,910.87 [exec] Removing 7% discount [exec] Cost of Order 1111: $679.45 [exec] Cost of Order 4312: $2,011.44 [exec] Average price of all parts: $117.55 [exec] Total price of parts for Vendor 100: $501.06 [exec] Ordered list of vendors for order 1111 [exec] 200 Gadget, Inc. Mrs. Smith [exec] 100 WidgetCorp Mr. Jones [exec] Counting all line items [exec] Found 6 line items [exec] Removing Order 4312 [exec] Counting all line items [exec] Found 3 line items [exec] Found 1 out of 2 vendors with 'I' in the name: [exec] Gadget, Inc.
The roster Application (self study) • maintains team rosters for players in recreational sports leagues • four components: • Java Persistence API entities (Player, Team, and League) • a stateful session bean (RequestBean) • an application client (RosterClient) • three helper classes (PlayerDetails,TeamDetails, and LeagueDetails) • similar to the order application • two new features • many-to-many relationships • automatic table creation at deploytime
roster Application: source files • entity • League.java • Player.java • Team.java • request • Request.java • RequestBean.java • util • LeagueDetails.java • PlayerDetails.java • TeamDetails.java • order-app-client • RosterClient.java
roster application: output [echo] running application client container. [exec] List all players in team T2: [exec] P6 Ian Carlyle goalkeeper 555.0 [exec] P7 Rebecca Struthers midfielder 777.0 [exec] P8 Anne Anderson forward 65.0 [exec] P9 Jan Wesley defender 100.0 [exec] P10 Terry Smithson midfielder 100.0 [exec] List all teams in league L1: [exec] T1 Honey Bees Visalia [exec] T2 Gophers Manteca [exec] T5 Crows Orland [exec] List all defenders: [exec] P2 Alice Smith defender 505.0 [exec] P5 Barney Bold defender 100.0 [exec] P9 Jan Wesley defender 100.0 [exec] P22 Janice Walker defender 857.0 [exec] P25 Frank Fletcher defender 399.0