HomeDigital EditionSys-Con RadioSearch Java Cd
Advanced Java AWT Book Reviews/Excerpts Client Server Corba Editorials Embedded Java Enterprise Java IDE's Industry Watch Integration Interviews Java Applet Java & Databases Java & Web Services Java Fundamentals Java Native Interface Java Servlets Java Beans J2ME Libraries .NET Object Orientation Observations/IMHO Product Reviews Scalability & Performance Security Server Side Source Code Straight Talking Swing Threads Using Java with others Wireless XML
 

As I sit down to write this article, the hype for Star Wars Episode 1: The Phantom Menace is even greater than the Java industry hype before the release of the Enterprise JavaBeans specification 1.0! I couldn't help including a few references of my own to the beloved trilogy in hopes of adding a little flavor to an otherwise drab topic: persisting data.

Enterprise JavaBeans Persistence: Two Persistence Models
"Would you like the window or the aisle, sir?" asks the Intergalactic Travel ticket agent. Decisions, decisions! Does it matter? Well, maybe. That depends on a number of factors. Hmmm....Are you flying into the magnificent city of Coruscant or bound for barren Tatooine? Is the seat adjacent to the window seat occupied by Darth Maul?

Life is all about options, and the development of business applications is no different. Fewer options amount to less flexibility; however, limiting your choices certainly simplifies the decision process. On the other hand, more options means more flexibility for your application, albeit at the cost of lengthy debate over which choice is best for you. This month's topic discusses the choices available when you implement persistence with entity beans in your Enterprise JavaBeans application.

Entity Bean State Management
The Enterprise JavaBeans 1.0 (and newly released 1.1) specification attempts to simplify decisions about persistence by providing a straightforward persistence model for managing the state of entity beans (note that entity bean support is not mandatory in 1.0 of the EJB specification, but is mandatory for EJB 1.1 compliance). State management refers to the creation, destruction, loading and storage of persistent data in an entity bean. The EJB specification defines a small set of methods to perform these important services: ejbCreate, ejbLoad, ejbStore, ejbRemove, ejbActivate and ejbPassivate. We're particularly interested in the first four, which represent the CRUD (Create, Read, Update and Delete) operations typically seen in a persistent application. Over the course of this article you'll become intimate with these methods and their state management responsibilities through the Intergalactic Travel ticket system examples.

Besides describing the methods for managing an entity bean's state, the EJB specification offers two models of persistence: bean managed and container managed. However, as we've noted, multiple options can lead to confusion and extra decisions you have to make to meet your project's deadline...which was yesterday. Each model has its advantages and disadvantages, of course. This article highlights the semantics and trade-offs of the two EJB persistence models, providing you with ammunition to decide quickly and easily which one best suits your needs.

The Intergalactic Travel ticket system provides a good illustration of the two persistence models. For our purposes, a simple entity bean that represents a persistent luxury liner ticket will suffice. Figure 1 reveals the UML class diagram of the TicketEntityBean; Table 1 depicts the RDBMS storage schema for this entity bean. This month's example enterprise beans were written to the EJB 1.0 spec and deployed using a BEA WebLogic Application Server 3.1.4.

Figure 1 Table 1

Bean-Managed Persistence
Bean-managed persistence refers to situations in which an entity bean manages its own state through the implementation of persistence methods via JDBC, object serialization, etc. To code an entity bean with bean-managed persistence, you must implement the relevant operations to create, store and load your entity bean from its persistent storage format. Let's take a look at an example entity bean from the Intergalactic Travel ticket system that implements bean-managed persistence. The jdj.Ticketing.beanmanaged.Ticket-EntityBean (TicketEntityBean for short) contains JDBC SQL calls to handle storage and retrieval of the bean from our MS Access RDBMS.

Intergalactic Travel ticket agents issue new tickets as passengers reserve seats and pay in credits for the flight. The life cycle of our TicketEntityBean begins when we invoke a create method through our factory interface class, TicketEntityHome. An entity bean's home interface can provide multiple "create" methods, each having a corresponding ejbCreate() method on its entity bean. This method is called from the home interface class via its container, and allows you to initialize your entity bean accordingly. In our example we have just one create method, which takes all attributes necessary to create a fully formed TicketEntityBean. Listing 1 demonstrates how the ejbCreate() method for our bean-managed TicketEntityBean not only sets the entity bean's attributes, but also establishes a connection to the database, prepares a JDBC statement and executes an insert statement into the persistent store. The TicketEntityBean contains helper methods to promote reuse of code. They're shown in Listing 2.

Next, to access our existing TicketEntityBean, we go through the TicketEntityHome once again and call the home.findByPrimaryKey(TicketEntityPK pk) method. In the case of our bean-managed persistence entity bean, this call is forwarded to the ejbFindByPrimaryKey() method of an empty instance of the TicketEntityBean. TicketEntityBean.ejbFindByPrimaryKey() reads in the appropriate information from the ticket table in MS Access and populates the entity bean. Eventually we receive a remote reference, TicketEntity, from the TicketEntityHome. Just as in the ejbCreate() method, you have to write all the code necessary to access the database.

JDBC calls to fetch our entity bean data are located in a single helper method, read(). The entity bean may be loaded in two ways: ejbFindByPrimaryKey() and ejbLoad(). Following good OO form, the code is written in a single read() method and called from each "load" method to achieve localization and reuse. Listing 3 demonstrates calling read() from our ejbFindByPrimaryKey() method.

Now that we have our TicketEntity reference, we can modify it by changing the arrival city (e.g., from Coruscant to the Mos Eisley Spaceport on Tatooine) or the flight number. After an operation is performed and its transaction committed, the TicketEntityBean's container will issue an ejbStore() to save the current state of the entity bean to persistent storage. Invoking ejbStore() on our TicketEntityBean will cause the following actions: get a connection to the database, prepare an update statement and execute a SQL Update through JDBC to the ticket table. Again, you have to code all of the relevant logic by hand for SQL database access, connection management and exception handling. Listing 4 demonstrates a bean-managed update.

What if a ticket is invalid and an Intergalactic Travel ticket agent wishes to delete the bad ticket from the database? In EJB you have the flexibility to remove an entity bean in two different ways: indirectly, through the entity bean's Home Interface.remove(myPrimaryKey pk) method, or directly, through the entity Bean.remove() method. Either way, the correct entity bean is located by the container and the ejbRemove() method is called. In the case of a bean-managed entity bean, you must code the JDBC calls to effectively delete the row from the ticket table. This code is illustrated in Listing 5.

Finally, to allow a ticket agent to see a list of valid tickets issued for a particular space flight, we need to provide a mechanism to query our persistent store of tickets and return this list. To do so will require a search method against the ticket table by flight number.

In EJB, finder methods on entity beans provide the means to return an enumeration of valid results. Finder methods are located on the home interface of the appropriate entity bean; thus, to search for all tickets issued for a specific flight, we have created a method, findTicketsByFlight(int aFlightNumber), on TicketEntityHome, our bean-managed entity's home interface. As usual, the home interface class finder method delegates to an entity bean instance to do the dirty work. The code necessary to return this list is executed in the TicketEntityBean.ejbFindTicketsByFlight() method (see Listing 6). Within ejbFindTicketsByFlight() a JDBC ResultSet is returned from a query, and primary keys for each ResultSet row are instantiated and returned. The home interface class uses this list of primary keys to fetch to the appropriate entity bean instances and return an enumeration of TicketEntity proxies to the caller.

Bean-managed persistence has numerous admirable qualities including development flexibility and the ability to allow developers to write database access code tailored for performance. For instance, complex searches can be coded into entity bean ejbFinder methods, and entity beans representing data from multiple sources can be coded easily through bean-managed persistence (if your EJB server provider doesn't support mapping multiple tables to a single container-managed entity bean). In addition, developers can access their JDBC ResultSet directly, and tune this code for high performance as needed.

However, it clearly takes considerable work to create a bean-managed entity bean. Besides being tedious to design and implement, managing persistence inside your own beans exposes you to coding errors and limits portability and reusability.

With bean-managed persistence you must code all database access yourself. This can lead to error-prone code and a retesting nightmare when your entity bean's attributes change. You must remember to handle database exceptions correctly and always close resources that might be left hanging from an error.

You must also make your own connection to the database, which may involve creating a new connection each time if your EJB server doesn't provide a mechanism to return existing connections from a pool. Creating a new connection for each database call is costly and ill advised in a high-volume environment.

The topic of ensuring EJB portability would take a whole article or two in itself (in an upcoming issue); essentially, managing your own connections reduces bean portability. Do you see any hard-coded references to WebLogic in our example? What if we decide to port our entity bean to another EJB server? All references to WebLogic would have to be found and replaced.

Finally, what if you wish to port your bean to another storage mechanism? If you'd like to reuse the bean-managed TicketEntityBean in a file-storage schema, you're in for some heavy code modifications!

To solve these problems, EJB provides container-managed persistence.

Container-Managed Persistence
Container-managed persistence relies on the EJB server to generate the appropriate code to manipulate your entity bean. Specifically, the entity bean's persistence services are handled by its container, which transparently manages the bean's persistent state. No data storage coding is demanded from developers of container-managed entity beans. Developers simply write business logic within the entity bean and leave the responsibility for mapping a storage schema in the entity bean's deployment descriptor up to the bean's deployer. It's important to note that the EJB 1.0/1.1 specification doesn't lay the groundwork for how container-managed persistence is to be implemented; thus each EJB server typically provides unique implementations of these services through proprietary containers. While one may store entity beans only as serialized objects, another may offer a whole gamut of options ranging from file-based persistence to storage in an RDBMS or an ODBMS.

So how does a container-managed entity bean differ from our bean-managed entity bean? To understand the differences we'll look at the entity bean class: jdj.Ticketing.containermanaged.TicketEntityBean as well as jdj.Ticketing.containermanaged.file.TicketEntityBean (TicketEntityBean, for short). These classes represent the same bean-managed TicketEntityBean just discussed, but delegate persistence to their containers instead.

Container-Managed TicketEntityBean
A glance at TicketEntityBean.ejbCreate() in Listing 7 reveals the first of many dramatic differences in the bean-managed implementation versus the container-managed implementation of our TicketEntityBean. Initialization of its attributes with the values passed is the extent of the logic performed by the container-managed entity bean. After the execution of ejbCreate(), the entity bean's container will act on behalf of it, performing an insert into the appropriate storage device (in our case a file or an MS Access DB). No coding of complex JDBC calls, connection management or exception handling was required to save our container-managed entity.

Similarly, we see that the JDBC code from our bean-managed entity bean has been removed from the following methods: ejbLoad(), ejbStore() and ejbRemove(). In each case the container executes the appropriate code for the retrieval, storage and removal of our TicketEntityBean.

Finally, the helper methods used in the bean-managed example are unnecessary in this case. We no longer need the custom read(), getConnection(), close(), static initializer of our database driver class or the ejbFinder method ejbFindTicketsByFlight(). Functionality previously offered in these methods is handled transparently by the container-managed entity bean's container!

Component-Based Development Is the Key
You'll notice no difference between the JDBC and file-based container-managed TicketEntityBean classes (including primary key, home and remote interface classes [not shown but available for download at www.JavaDevelopersJournal.com]). In fact, a VDIFF on the entity bean files will show no change except for the package name (made for demo purposes only) on all files. Component-based development tools allow us to change the bean's functionality at deployment rather than during development - and all without a single code change.

Enterprise JavaBean's container-managed persistence provides tremendous advantages over bean-managed persistence. Its component-based approach to writing and deploying persistent objects reduces development time by shielding you from writing complex storage code. This allows you to concentrate on business logic within the bean instead of connection management, file resource management, data access and exception handling.

Container-managed persistence also promotes bean portability by not locking your entity beans into a particular storage scheme. Not one line of code had to be modified to deploy our entity bean from an RDBMS storage schema to a file-based schema. Compare that to what needs to be done to convert our bean-managed TicketEntityBean. I'll leave that exercise to you...and may the Force be with you!

However, while container-managed persistence is a powerful option, it does fall short in some areas. For instance, some EJB servers may provide robust mapping of entity beans to multiple tables while others may only allow a one-to-one mapping of table-to-entity bean. In this case you must either write a bean-managed entity bean or write multiple container-managed entity beans and guarantee they always work within the same transaction.

In addition, complex queries may not be possible with the finder method capabilities of today's EJB deployment facilities. The EJB specification 1.0 did not state how to declare container-managed finder methods; thus each EJB server vendor has a different means of deploying your entity bean's finder methods. One vendor may provide functionality that another does not. The EJB 1.1 standard based on XML will hopefully provide more harmonious deployment services between vendors.

Container-Managed Persistence: Today and Tomorrow
The EJB specification is just that, a specification. It allows different vendors to implement the required interfaces as needed. EJB server vendors have been providing container implementations to handle container-managed persistence to RDBMS and file-based stores.

Today, ODBMS vendors such as Versant Corporation (www.versant.com) are assuming the role of EJB Container Provider by developing containers that understand how to save entity beans to their object databases. Currently, third-party containers such as the VERSANT Enterprise Container are being built for specific EJB server vendors such as the BEA WebLogic Application Server. However, once the EJB specification provides guidelines for container implementations, third-party containers will also be portable across EJB servers. These containers will plug into existing EJB servers, providing value-added functionality to your application out-of-the-box.

On the deployment side of entity beans, rumor has it that Symantec's (www.symantec.com) VisualCafé product will soon include modules that offer a common deployment interface to popular EJB servers such as IBM's WebSphere and BEA WebLogic's application servers. Thus you'll be able to deploy a bean to either without needing to understand the nuances of each EJB server's entity bean deployer.

Conclusion
We've covered the two models of persistence offered in the EJB specification 1.0/1.1 - bean managed and container managed - and the advantages and disadvantages of each. Just as a window seat may be optimal on one flight and suboptimal on the next, one model or a mixture of the two will provide a best fit for your application's needs.

Bean-managed persistence offers you the ability to perform complex queries or map entity beans to multiple data sources, yet it lacks portability, reusability and simplicity, requiring knowledge of complex storage mechanisms and connection management. Container-managed persistence has its faults as well, such as a lack of entity bean deployment standards that allows vendors to offer various degrees of functionality in their products. However, the component-based features of container-managed persistence promote entity bean portability and reuse while simplifying the development of persistent objects, allowing you to focus on business logic. The end result: more robust applications built in record time at a fraction of the cost of traditional development techniques!

With EJB you have the flexibility to choose the correct persistent model for your needs. Recognizing that too many options can result in one's downfall, I hope you have been enlightened sufficiently concerning EJB persistence that you'll be able to make the right choice quickly, and soon be off doing fun stuff like coding Java...or viewing The Phantom Menace again and again!

Author Bio
Jason Westra is a managing partner with Verge Technologies Group, Inc., a Java consulting firm specializing in Enterprise JavaBeans solutions.
He can be contacted at [email protected].

	

Listing 1: Bean-managed Create 

// ejbCreate() inserts Entity Bean 
public TicketEntityPK ejbCreate 

(int aTicketNum, double aPrice, 
 int aFlightNumber, String aSeatNumber, 
 Date aDepartDt, Date aArrivalDt, 
 String aDepartCity, String aArrivalCity, 
 int aPassengerNumber) 
throws CreateException 
{ 

// set attributes into Entity Bean to 
// insert 
    ticketNum = aTicketNum; 
    price = aPrice; 
    flightNumber = aFlightNumber; 
    seatNumber = aSeatNumber; 
    departDt = aDepartDt; 
    arrivalDt = aArrivalDt; 
    departCity = aDepartCity; 
    arrivalCity = aArrivalCity; 
    passengerNumber = aPassengerNumber; 
  
// mark as modified 
    isModified = true; 
  
    Connection con = null; 
    PreparedStatement ps = null; 
    try{ 
       con = getConnection(); 
       ps = con.prepareStatement( 
    "insert into Ticket (ticketNum, 
    price, "+ "flightNumber, seatNumber, 
    "+ "departDt, arrivalDt, departCity, 
    "+ "arrivalCity, passengerNumber) "+ 
    "values (?, ?, ?, ?, ?, ?, ?, ?, ?)"); 
  
// fill values from TicketEntityBean 
// into PreparedStatement 
       ps.setInt(1, ticketNum); 
       ps.setDouble(2, price); 
       ps.setInt(3,flightNumber); 
       ps.setString(4,seatNumber); 
       ps.setDate(5, departDt); 
       ps.setDate(6,arrivalDt); 
       ps.setString(7,departCity); 
       ps.setString(8, arrivalCity); 
       ps.setInt(9,passengerNumber); 
  
       if (ps.executeUpdate() != 1) 
       { 
       throw new CreateException 
       ("Failed to insert ticket: 
    "+ticketNum); 
       } 
       TicketEntityPK pk = 
       new TicketEntityPK(ticketNum); 
  
        return pk; 
    } 
    catch (CreateException ex){ 
       throw ex; 
    } 
    catch (SQLException sqlEx) { 
        throw new CreateException 
        (sqlEx.getMessage()); 
    } 
    finally { 
       close(ps, con); 
    } 
} 

Listing 2: Helper methods for TicketEntityBean 

// Static initializer in TicketEntityBean // class 
static 
{ 

// initialize weblogic.jdbc.jts.Driver 
   new weblogic.jdbc.jts.Driver(); 
} 

// Entity Bean helper methods 

private void close 
(PreparedStatement aPS, Connection aCon) 
{ 
// final attempt to close the 
// PreparedStatement and Connection 
  try { 
    aPS.close(); 
    aCon.close(); 
  } 
  catch (Exception ex) {} 
} 
  
public Connection getConnection() 
  throws SQLException 
{ 
// get an open DBconnection from the 
// ejbPool 
  return DriverManager.getConnection 
    ("jdbc:weblogic:jts:ejbPool"); 
} 

Listing 3: Bean-managed Read 

public TicketEntityPK ejbFindByPrimaryKey 
  (TicketEntityPK pk) 
  throws FinderException, RemoteException { 

// ejbFindByPrimaryKey fetches the Entity // Bean 

  if ((pk == null)) 
    throw new FinderException 
      ("Invalid parameter. "+ 
        "Primary Key cannot be null"); 
  
      System.out.println("ejbFindByPrima       ryKey()"); 
  
// call helper method 
    read(pk); 
    return pk; 
} 

private void read(TicketEntityPK pk) 
throws RemoteException, FinderException { 
  
// reads data from Ticket table 
// into TicketEntityBean 
  Connection con = null; 
  PreparedStatement ps = null; 
  try{ 
    con = getConnection(); 
    ps  = con.prepareStatement 
    ("select * from Ticket "+ 
    "where ticketNum = ?"); 
  
    ps.setInt(1, pk.ticketNum); 
    ps.executeQuery(); 
    ResultSet rs = ps.getResultSet(); 
  
// map data into Entity Bean 
    if (rs.next()) { 
      ticketNum = rs.getInt(1); 
      price = rs.getDouble(2); 
      flightNumber = rs.getInt(3); 
      seatNumber = rs.getString(4); 
      departDt = rs.getDate(5); 
      arrivalDt = rs.getDate(6); 
      departCity = rs.getString(7); 
      arrivalCity = rs.getString(8); 
      passengerNumber = rs.getInt(9); 
  
      isModified = false; 
    } 
    else { 
      throw new FinderException 
        ("Read Error: TicketEntityBean "+ 
           pk.ticketNum + " not found"); 
    } 
  } 
  catch (SQLException sqlEx) { 
           throw new RemoteException 
                (sqlEx.getMessage()); 
  } 
  finally { 
    close(ps, con); 
  } 
} 

Listing 4: Bean-managed Update 

public void ejbStore() 
throws RemoteException 
{ 

// saves Entity Bean to persistent storage 
  if (!isModified()) 
      return; 
  
  Connection con = null; 
  PreparedStatement ps = null; 
  try { 
    con = getConnection(); 
    ps = con.prepareStatement 
    ("update Ticket set ticketNum = ?,"+ 
     "price = ?, flightNumber = ?, "+ 
     "seatNumber = ?, departDt = ?, "+ 
     "arrivalDt = ?, departCity = ?, "+ 
     "arrivalCity = ?, passengerNumber = 
    ?"+ "where ticketNum = ?"); 
  
// fill values from TicketEntityBean 
// into PreparedStatement 
    ps.setInt(1, ticketNum); 
    ps.setDouble(2, price); 
    ps.setInt(3,flightNumber); 
    ps.setString(4,seatNumber); 
    ps.setDate(5, departDt); 
    ps.setDate(6,arrivalDt); 
    ps.setString(7,departCity); 
    ps.setString(8, arrivalCity); 
    ps.setInt(9,passengerNumber); 
// extra for PrimaryKey where clause 
    ps.setInt(10, ticketNum); 
  
    int i = ps.executeUpdate(); 
    if (i == 0) { 
      throw new RemoteException 
      ("Failed to update TicketEntityBean: 
    " + ticketNum); 
    } 
  
    isModified = false; 
  } 
  catch (RemoteException ex) 
  { 
     throw ex; 
  } 
  catch (SQLException sqlEx) 
  { 
     throw new RemoteException 
              (sqlEx.getMessage()); 
  } 
  finally 
  { 
     close(ps, con); 
  } 
} 

Listing 5: Bean-managed Delete 

public void ejbRemove() 
throws RemoteException 
{ 
// deletes Entity Bean from 
// persistent storage 
  Connection con = null; 
  PreparedStatement ps = null; 
  try { 
    con = getConnection(); 
  
    TicketEntityPK pk = 
    (TicketEntityPK) ctx.getPrimaryKey(); 
    ps= con.prepareStatement 
    ("delete from Ticket where ticketNum =      ?"); ps.setInt(1, pk.ticketNum); 
  
    int i = ps.executeUpdate(); 
    if (i == 0) { 
      throw new RemoteException 
      ("Delete failed. TicketNumber: " 
      + pk.ticketNum + " not found"); 
    } 
  } 
  catch (RemoteException ex) { 
    throw ex; 
  } 
  catch (SQLException sqlEx) { 
    throw new RemoteException (sqlEx.getMessage()); 
  } 
  finally { 
    close(ps, con); 
  } 
} 
  

Listing 6: Bean-managed finder: ejbFindTickets By Flight() 

public Enumeration ejbFindTicketsByFlight 
  (int aFlightNumber) 
  throws FinderException, RemoteException 
{ 
  Connection con = null; 
  PreparedStatement ps = null; 
  ResultSet rs = null; 
  try { 
    con = getConnection(); 
    ps = con.prepareStatement 
    ("select ticketNum from Ticket "+ 
      "where flightNumber = ?"); 
    ps.setInt(1, aFlightNumber); 
    ps.executeQuery(); 
    rs = ps.getResultSet(); 
  
    Vector ret = new Vector(); 
    TicketEntityPK pk; 
  
    while (rs.next()) 
    { 
         pk = 
      new TicketEntityPK(rs.getInt(1)); 
        ret.addElement(pk); 
    } 
  
    rs.close(); 
    return ret.elements(); 
  } 
  catch (SQLException sqlEx) { 
    throw new FinderException 
    (sqlEx.getMessage()); 
  } 
  finally { 
    try { 
      if (rs != null) rs.close(); 
      if (ps != null) ps.close(); 
      if (con!= null) con.close(); 
  } 
    catch (Exception done) {} 
  } 
} 

Listing 7: Container-managed JDBC TicketEntiyBean 

package jdj.ticketing.containermanaged; 

import java.lang.*; 
import java.rmi.*; 
import java.sql.Date; 
import javax.ejb.*; 

/* 
* Example of a container-managed Entity Bean 
*/ 
public class TicketEntityBean extends Object 
  implements EntityBean 
{ 
// TicketEntityBean business attributes 
  public int ticketNum; 
  public double price; 
  public int flightNumber; 
  public String seatNumber; 
  public Date departDt; 
  public Date arrivalDt; 
  public String departCity; 
  public String arrivalCity; 
  public int passengerNumber; 
  
// tells whether or not data was 
// actually modified 
  private boolean isModified; 
  
// needed by Entity Bean specification 
  transient protected EntityContext ctx; 
  
// Business methods for TicketEntityBean 
// Getter/Setter methods not shown in 
// Listing… Methods to satifsy Entity Bean // interface 
  public void ejbCreate 
    (int aTicketNum, double aPrice, 
    int aFlightNumber, String aSeatNumber, 
    Date aDepartDt, Date aArrivalDt, 
    String aDepartCity, String 
    aArrivalCity, 
    int aPassengerNumber) 
  { 
// set attributes to insert 
    ticketNum = aTicketNum; 
    price = aPrice; 
    flightNumber = aFlightNumber; 
    seatNumber = aSeatNumber; 
    departDt = aDepartDt; 
    arrivalDt = aArrivalDt; 
    departCity = aDepartCity; 
    arrivalCity = aArrivalCity; 
    passengerNumber = aPassengerNumber; 
  
// mark as modified 
    isModified = true; 
  } 
  
  public void ejbPostCreate 
    (int aTicketNum, double aPrice, 
    int aFlightNumber, String aSeatNumber, 
    Date aDepartDt, Date aArrivalDt, 
    String aDepartCity, String aArrivalCi     ty,int aPassengerNumber) 
  { 
// do nothing 
  } 
  public void setEntityContext(EntityContext aCtx) 
  { 
    ctx = aCtx; 
  } 
  
  public void unsetEntityContext() 
  { 
    ctx = null; 
  } 
  public void ejbRemove() 
  { 
// do nothing 
  } 
  
  public void ejbActivate() 
  { 
// do nothing 
  } 
  
  public void ejbPassivate() 
  { 
// do nothing 
  } 
  
  public void ejbLoad() 
  { 
// do nothing 
  } 
  
  public void ejbStore() 
  { 
// do nothing 
  } 
} 

Listing 8: Container-Managed File TicketEntityBean 

package jdj.ticketing.containermanaged.file; 

import java.lang.*; 
import java.rmi.*; 
import java.sql.Date; 
import javax.ejb.*; 

/* 
*   Example of a container-managed Entity Bean 
*/ 
public class TicketEntityBean extends Object 
  implements EntityBean 
{ 
// TicketEntityBean business attributes 
  public int ticketNum; 
  public double price; 
  public int flightNumber; 
  public String seatNumber; 
  public Date departDt; 
  public Date arrivalDt; 
  public String departCity; 
  public String arrivalCity; 
  public int passengerNumber; 
  
// tells whether or not data was 
// actually modified 
  private boolean isModified; 
  
// needed by Entity Bean specification 
  transient protected EntityContext ctx; 
  
// Business methods for TicketEntityBean 
// Getter/Setter methods not shown in 
// Listing… Methods to satifsy Entity Bean // interface 
  public void ejbCreate 
    (int aTicketNum, double aPrice, 
    int aFlightNumber, String aSeatNumber, 
    Date aDepartDt, Date aArrivalDt, 
    String aDepartCity, String aArrivalCi     ty, int aPassengerNumber) 
  { 
// set attributes to insert 
    ticketNum = aTicketNum; 
    price = aPrice; 
    flightNumber = aFlightNumber; 
    seatNumber = aSeatNumber; 
    departDt = aDepartDt; 
    arrivalDt = aArrivalDt; 
    departCity = aDepartCity; 
    arrivalCity = aArrivalCity; 
    passengerNumber = aPassengerNumber; 
  
// mark as modified 
    isModified = true; 
  } 
  
  public void ejbPostCreate 
    (int aTicketNum, double aPrice, 
    int aFlightNumber, String aSeatNumber, 
    Date aDepartDt, Date aArrivalDt, 
    String aDepartCity, String aArrivalCity, 
    int aPassengerNumber) 
  { 
// do nothing 
  } 
  public void setEntityContext(EntityCon     text aCtx) 
  { 
    ctx = aCtx; 
  } 
  
  public void unsetEntityContext() 
  { 
    ctx = null; 
  } 
  public void ejbRemove() 
  { 
// do nothing 
  } 
  
  public void ejbActivate() 
  { 
// do nothing 
  } 
  
  public void ejbPassivate() 
  { 
// do nothing 
  } 
  
  public void ejbLoad() 
  { 
// do nothing 
  } 
  
  public void ejbStore() 
  { 
// do nothing 
  } 
} 


  

 

All Rights Reserved
Copyright ©  2004 SYS-CON Media, Inc.
  E-mail: [email protected]

Java and Java-based marks are trademarks or registered trademarks of Sun Microsystems, Inc. in the United States and other countries. SYS-CON Publications, Inc. is independent of Sun Microsystems, Inc.