Tài liệu hạn chế xem trước, để xem đầy đủ mời bạn chọn Tải xuống
1
/ 71 trang
THÔNG TIN TÀI LIỆU
Thông tin cơ bản
Định dạng
Số trang
71
Dung lượng
191,04 KB
Nội dung
passivated state. Where Do My Error Messages Go? In these examples we've been showing the code printing out to System.err or System.out. After all, your code is embedded in a Web server somewhere; it's not as though you have a nice command line on which to view all the exception traces. So where do they go? The answer depends on the EJB server software you are running. For example, the reference implementation puts them in the $j2ee.home/logs/machine_name/application_name directory. You will need to look up the documentation for your environment for more information. In a future release of the J2EE environment, you will be able to use the new Java logging capability included in J2SE 1.4. This will give you even more control over your logging capabilities. However, as logs are files, logging will still be controlled somewhat by the restrictions placed on EJBs, which we outlined earlier in the chapter. Because stateful session beans can have this intermediate step, their lifecycle is a little more complex. Figure 16−2 shows the difference. Notice how, in comparison to the simple Figure 16−1, that there is an intermediate state. The intermediate state represents the time when your stateful session bean has been passivated. Figure 16−2: The lifecycle of a stateful session bean While your mailer bean does not need to handle passivation (there is no state to be saved), it will be implemented anyway as an exercise. When the bean is about to be serialized, you don't want it to keep any information about the mail system in use. There really isn't any need for it, so you might as well remove the reference. The number formatter can stay, though, because it is not causing you any harm. This makes the ejbPassivate() method body really simple: public void ejbPassivate() { mailSession = null; smtpService = null; } Recovering from passivation (activation) requires you to undo the effects that you've just created. Now you must establish those references again. You may remember that you did exactly this in the ejbCreate() method: So why not re−use the code here? Instead of just copying the code, you will shuffle it a little bit so that you now have a common internal method — createMailSession(): private void createMailSession() { Chapter 16: Introducing Enterprise JavaBeans 347 Properties props = new Properties(); String mailhost = "mail.mycompany.com"; props.put("mail.host", mailhost); props.put("mail.transport.protocol", "smtp"); props.put("mail.smtp.host", mailhost); mailSession = Session.getDefaultInstance(props); try { smtpService = mailSession.getTransport(); } catch(MessagingException nspe) { // SMTP is one of the defaults. If we get this // there is a serious problem! // Should throw an EJBException System.err.println("Danger, Danger! " + "No SMTP mail provider!"); } } With this method created, ejbCreate() loses a collection of code, and the ejbActivate() only has one task to do — call this method: public void ejbCreate() { formatter = NumberFormat.getNumberInstance(); formatter.setMinimumFractionDigits(2); formatter.setMaximumFractionDigits(2); createMailSession(); } public void ejbActivate() { createMailSession(); } That's it. A complete session bean now exists. As you have taken a completely minimalistic approach to the design and implementation of this particular bean, you can deploy it as either a stateless or stateful session bean. Entity beans Of all the bean types, session beans are the easiest to implement. Their behavior is relatively simple, and you have only a few methods to implement and rules to live by. Now you're ready for the next level — entity beans. Entity beans are, by nature, long−lived objects. An entity bean is typically classified as a bean that directly represents some underlying data source, such as a database. When you ask for an entity bean, it will probably already exist, and you will just be given the handle to it. When you have finished with the bean, it doesn't just go back into the pool because there are maybe another 10 client applications that are all making use of the same entity bean. Generally an entity bean is created immediately when the server is started. When the server shuts down or crashes, that does not destroy the bean; it is more a case of suspended animation. As soon as the server restarts, that bean will exist again in exactly the same state it was in when you left it. Chapter 16: Introducing Enterprise JavaBeans 348 Types of entity beans As with session beans, there are two types of entity beans. The types are defined by how you get data into and out of the bean: Broadly speaking, either the bean manages the data, or the EJB server manages the data. When the bean itself manages both the data and keeping up to date with underlying data source, this is termed Bean−Managed Persistence (BMP). When you are referring to the bean itself, it is a Bean−Managed Entity Bean. In this form, the bean, whenever it becomes passivated or activated, must look after re−establishing the database connections or whatever other internal systems it might need. In some respects, this is similar to the way in which stateful session beans must work. On the other end of the spectrum are entity beans that let the EJB server manage all their capabilities and data: This is Container−Managed Persistence (CMP). These beans are then called Container−Managed Entity Beans. Each of these terms is a mouthful, so usually the "entity" part is dropped. Bean management is much simpler to implement than container management. A bean−managed persistence scheme is very similar to what you have already seen with stateful session beans. Container−managed beans require a lot more interaction between the bean and the EJB server and home−interface code. In addition, there is a lot of extra work to do outside the bean, including learning yet another language. For this reason, we'll stick with the simpler form for the remainder of this chapter. Pinning down entity beans Rules, rules. No matter where we go, we just can't escape them! Writing entity beans is no different. In addition to the basic rules about what EJBs can and cannot do, entity beans add a few more. Most of these rules are brought about because of the required behavior of representing an item in a database, so let's try to define how an entity bean works. Entity beans represent some real data in an underlying database. If you need something to do quick calculations, write a session bean. This means that the bean is a thin veneer over the underlying data. Where you search a database for a row or rows in a table, a bean represents the result of that search, encoded in Java. Hang on! Isn't that what JDBC is about? Also, if an entity bean is just a veneer over the database, why not just use the database directly rather than going through all this extra overhead? Take a step back. What is Java programming, and in more general, object−oriented programming all about? The most fundamental purpose is to put together little pieces of data and the code that acts on that data all in one lovely gift−wrapped box — preferably black in color. When you hand someone that item, they really don't care what's inside it, just that it works as advertised. In Java, everything starts right at the bottom — a single common class that everyone uses (java.lang.Object). As you move up the food chain, things get more and more complex. Classes start containing more than just data — they become composites of other classes. The ultimate class becomes the application or applet or servlet or whatever. The EJB is just one level in the process. The bean takes all the information in the database, wraps it up in some pretty clothing, and allows others to take it to the dance. When you're building huge enterprise applications, the EJB makes it much easier to follow code when you start passing around instances of the Order class, rather than an array of strings and integers. Having that class means that you only need to write the code once that deals with the data, rather than something for every time you want to use it. So that completes your theory lesson on object−oriented programming. What does it all mean? An entity bean, as an abstraction of some real, underlying data, is held to some of the same rules as that data. For example, a database contains tables, and each table contains many rows of data. Somehow you have to create these abstractions and map Java code to the database. You have two options here — one is to Chapter 16: Introducing Enterprise JavaBeans 349 encapsulate the entire table, and the other is to represent only a single row (or the result of a query to the database that may join multiple tables into a single result). For the novice, it probably makes the most sense to wrap the entire table in a single bean. After all, that enables you to build a heap of methods to query directly for data and rows of people in a simple, convenient fashion. Where this approach lets you down is that in most cases, that database is going to be huge. Worst of all, that huge data size translates to enormous amounts of memory consumption on the Java server. And, to throw one more problem into the ring — what if you want data that span multiple tables? These are all design issues that you should consider when building an entity−bean instance. No matter what you do, you have to be able to tell the system just which bean you want. Entity beans also use the home interface to locate bean instances (we'll cover implementing the home interface in the next section), but you also need some way to identify the bean you want. For example, in the database, it is easy to specify that you want a particular customer simply by using his or her unique ID (primary key) in the SQL SELECT statement. Entity beans have exactly the same context — a primary key that nominates a specific bean. If we say one bean "instance" is equivalent to one row of a relational database table, you can see the instant correlation between the two. Note In big systems, it is quite probable that a particular piece of data will be represented by more than one instance of your entity bean. When coding applications and beans, you should never assume that your bean is going to have only one instance. For example, the data underlying the bean could be changed by another instance. Be careful, and always assume that your data are not valid when processing information from an underlying database. The entity−bean interface has a way of enforcing the integrity of the data across multiple bean instances, but you should still keep it in mind when coding. Creating the remote interface Implementing an entity bean requires the same basic steps as implementing a session bean. For this example, we will show the implementation of the customer entity bean from our code. You start the process in the same way by creating a remote interface. This interface is no different from the interfaces used for session beans and so should present nothing out of the ordinary. The Customer remote interface is an interface that extends EJBObject. To this you add your normal business−method definitions. Again, you need to make sure that all the methods throw RemoteException as you can see from this definition of the Customer remote interface: public interface Customer extends EJBObject { public int getCustomerID() throws RemoteException; public void setCustomerID(int id) throws RemoteException; public String getName() throws RemoteException; public void setName(String name) throws RemoteException; public String getAddress() throws RemoteException; public void setAddress(String addr) throws RemoteException; public String getEmail() throws RemoteException; public void setEmail(String addr) throws RemoteException; public String getCountry() throws RemoteException; public void setCountry(String code) throws RemoteException; public String getPhoneNumber() throws RemoteException; public void setPhoneNumber(String ph) Chapter 16: Introducing Enterprise JavaBeans 350 throws RemoteException; } Writing the bean implementation Next you move on to the bean−implementation code. Again, you follow the same process as for session beans — with one small twist. This time, instead of implementing the SessionBean interface, the code must extend the EntityBean interface — which is fair enough, as you are creating an entity bean, not a session bean. In stubbing out the new methods of the entity bean, you will find that they match fairly well with session beans. All the familiar methods are there — ejbRemove(), ejbPassivate(), and ejbActivate(). Four new methods also make an appearance: ejbLoad(), ejbStore(), setEntityContext(), and unsetEntityContext(). Table 16−2 explains these new methods. Table 16−2: Methods of the EntityBean interface Method Description ejbLoad() Provides notification that your bean should reload its internal data from the underlying data source, as it may have changed. ejbStore() Provides notification that any changes that the current client may have made should be stored back in the database. setEntityContext() Provides notification of the context information that this bean is in. (Identical functionality to that of the session bean's setSessionContext() method.) unsetEntityContext() Provides notification that any previously set context information is now becoming invalid. The bean is about to be garbage−collected, so you should clean up any remaining information or links. Reading between the lines here, you may have noticed something interesting: The load and store events talk about reading and writing to the underlying data source. What does this mean? Well, the implication is that your bean does not need to maintain an absolutely live, completely synchronized link with the data source. The code is allowed to buffer changes locally. An example of where buffering changes locally might be appropriate is when your bean takes a lot of client information in a series of steps and then writes it all to the database. If you know that your bean is going to need to do this, you may make use of the JDBC batch−updating calls. At the time you know your bean becomes live for a client, you can immediately start to batch any updates by calling the addBatch() method of Statement rather than the direct executeQuery() method. Then, once you receive the notification through ejbStore(), the code can just call executeBatch() and update everything at once. This is a very useful tactic and a great way to optimize the performance of your application. Revisiting bean pooling Before moving on to discuss the implementation of a bean, think back to the issue of how the EJB server views a bean. As far as you know, the bean, when not being used by a client and sitting in the pool, is lying around in the Caribbean, sipping margaritas, waiting for the call−up to work. As far as entity beans are concerned, their lifestyle is a little more complicated than that. In the preceding sections, you might have gotten the idea that once an entity bean has been created for a particular piece of data (say a row in a database table), that piece of data is all it represents in its life. That is Chapter 16: Introducing Enterprise JavaBeans 351 not the case. Any entity−bean instance can be re−used for any similar piece of data. If you ask for a customer−entity bean, that given instance could be used to represent any customer in the database. So when you've finished with it, and it has gone back to sitting in the pool, the next time it is used it will probably represent a completely different customer. Each bean instance must be capable of being changed on demand. How does the code acquire this capability? Through the mysterious ejbCreate() method. We've mentioned this strange beast in passing many times before, but never really delved into its character properly. ejbCreate() is the method called by our EJB server on a particular instance when a client asks for a new bean. In session beans, this method is used to create an instance of the bean configured in some given way (the parameters passed to the create method). For entity beans, the role of the create methods changes somewhat. Under the entity−bean type, create methods resemble the more traditional "creation" role. That is, when a user calls the create() method on the home interface, it is a sign that he or she would like to make a new instance of that bean and the data that it represents underneath (for example, a new product). Your bean implementation is allowed to have as many different ejbCreate() methods as it thinks it needs. Naturally, these methods also conform to the normal method−declaration rules about parameter ordering and naming and so on, but you are not required to have only the version with no parameters. (You can even leave it out, but that really isn't a good idea.) What you are required to do for entity beans is return an instance of the primary key from the ejbCreate() method (remember, session beans are to return void). Figure 16−3 shows the basic life cycle of an entity bean and how the various method calls relate to this life cycle. Figure 16−3: The life cycle of an entity bean and the method calls used in each transition Tip It is not really a good idea to leave out the default, no−argument constructor or create() method. In the enterprise environment, you really should always provide a default way to access everything. So, according to this life cycle, it is quite possible that a bean will be instantiated, put to work representing an existing customer, released back to the pool, then pulled out of the pool to represent a new customer, and finally garbage−collected once it is done. Deciding on appropriate creation methods From the preceding discussion it is quite clear that the ejbCreate() methods play a very fundamental role in your entity−bean implementation. These methods are what enable you to create a bean that represents a new piece of data. So just what alternatives should you supply? When adding alternative parameter lists, you should consider how you want to let the user find and access a bean. For example, a customer bean should be able to be created based on the pre−selected customer ID (for example, a user name that the user has provided). You also want to provide a default method in case someone Chapter 16: Introducing Enterprise JavaBeans 352 wants to create a new customer where an ID does not yet exist. However, there is really no point to providing a creation method based on just a telephone number; though a creation method that provides all the properties of the bean is a good idea. It allows the client code to find out all the details before attempting to create the bean, and this in turn allows a little bit of pre−processing to be performed on the client to reject an application for a new customer before you get to the point of allocating expensive system resources to it (think — processing a sign−up Web page). Lifecycle of the Entity Bean Explained As you have already seen in Figure 16−3, the lifecycle of the entity bean is quite complex. We will now try to make sense of it for you. In the beginning, the bean did not exist. That's the single black circle on the left. At some point in time, the EJB container decides that it needs to load a few instances of your bean into a pool. (Typically this is done when the server first starts.) The pool contains beans that are not used by anyone. The server keeps them around just in case. To add an instance of your bean to the pool, the server starts by creating the instance using reflection (calling Class.forName().newInstance()). After instantiation, the entity context information is set using setEntityContext(). At this time your bean is in the pool and should be ready to perform any task. Once a bean is placed in the pool, there are three actions that it could be called on to do next: create a new instance in the underlying data source, represent an existing instance of data in the underlying source, or perform searches. When beans are sitting in the pool, they can still be performing useful tasks. Entity beans have three types of methods that could be called while in the pool: finders, selects, and home methods (home methods are covered later in the chapter and again in the next chapter). You could consider these method calls to be the same as static methods of a traditional Java class. That is, utility methods that can be called without needing to create an instance of the class. When these methods are called, your bean should not need to know about any of the other state information stored in the bean. They are quick, simple queries to return a search style request for information. In order to leave the pool, the bean has two options (well, three if you consider destroying the bean as a way of leaving). The first option is to represent a new piece of data. That is the role of the creation methods. When they are called, you should insert the appropriate row(s) into the underlying database. The second option is to represent a load of existing information. This is performed through the activation methods. When a bean is activated, it needs to check with the entity context about what piece of data it represents and then must fill its internal variables with any required information. In either option, your bean is now in the active state. Once active, a bean will occasionally change state. For example you write values to it (for example, change the address of the customer). Because your client code maintains a reference to that bean for some length of time, somehow that data must make it back to the database. That is the job of the ejbStore() method. When store is called, it is a request by the container to your bean to store its internal state in the database. Occasionally, your bean gets out of sync with the database, so the container will require the bean to make itself up to date again. This is performed through the ejbLoad() method. Note that at this time, you are just updating the state from a known start point. You really only want to check and update information that you already know about. It is not like the ejbActivate() call, where you must load/replace the entire state of the bean in memory. Chapter 16: Introducing Enterprise JavaBeans 353 Once your client code has decided it no longer needs the bean reference, the container is entitled to put it back into the pool. When this happens, the ejbPassivate() method is called. Alternatively, the client may want to delete the data from the underlying pool. This action is performed through the ejbRemove() method. Once back in the pool, that bean instance is once again able to go one of the three options. Just because the bean had to create a new data last time, does not mean that it will do the same next time it leaves the pool. Finally, the container decides it has too many bean instances sitting in the pool, or the server is going to shut down. The first thing your bean implementation knows about this is that the unsetEntityContext() method is called. Once that is called, it is all over for your code, and you can expect that your code will not be called any more. What are we going to provide for our customer entity bean then? Well, we've decided that we only want three variations: No arguments, so a person can create a new default user that has no data configured.1. A single−integer argument that is interpreted to be the customer ID. This will fetch the details of the nominated customer from the database. 2. Five parameters that correspond to the five columns of the customer database (the customer ID is automatically generated). This allows you to create a new customer with all the details set immediately. 3. The end result looks like this: public void ejbCreate() throws CreateException, EJBException { } public void ejbCreate(int id) throws CreateException, EJBException { } public void ejbCreate(String name, String addr, String email, String country, String phone) { throws CreateException, EJBException } Accessing and finding primary keys A couple of subsections ago we discussed the need for each bean to represent a single row in an underlying database. Part of this discussion was about the need for a unique identifier to enable you to access any given row simply and easily. So far we have not alluded to how the mapping of the unique identifier to a row in the database is performed in the bean code, and so now we need to cover this last piece of the bean puzzle. EJBs use the same primary−key concept as the relational database. For each entity bean, you must provide a class that uniquely identifies that bean. This class is referred to as the primary−key class and plays a vital role in the entity−bean framework. This class is not particularly special. In fact, no EJB interface exists for you to Chapter 16: Introducing Enterprise JavaBeans 354 extend. The only requirement is that this primary−key class, like all classes passed to and from beans, must be serializable. This class must present your internal code with an unambiguous way of locating a specific piece of pre−existing bean data. If you are representing a row in a database, that's simple — all your bean has to contain is the primary key for that row. For example, this is the complete primary key for the customer−entity bean: public class CustomerID implements Serializable { public int id; public CustomerID() { } public CustomerID(int id) { this.id = id; } } Public variables, a default constructor, and nothing else — very simple, isn't it? It really doesn't matter what the form of this class is, so long as you can make use of it in your code. In this case, all that is used is an integer that corresponds to the customer_id column of the Customer table. Tip Although the example class here uses a single item of data, primary key classes may choose to use a number of values. All that you must ensure is that the class is always unique for each bean instance you create. For classes that represent multiple items of data, make sure you override the default hashCode() and equals() methods so that your EJB code performs correctly. What good is a primary key without a way to use it? Primary keys are used in a number of new methods that are added to the bean implementation. These methods are called finder methods because you use them to locate bean instances and/or key information for other beans. Caution Finder methods are only implemented by you on bean−managed persistence−entity beans. When you use container−managed persistence, as we discuss in Chapter 17, they will not be implemented directly by you. The name of a finder method is required to start with ejbFind; as with the create methods, you can take any collection of parameters. Three further restrictions exist: The return value is required to be either the primary key class or an Enumeration or one of the collections classes (for example, List) of them. • You are required to have the method named ejbFindByPrimaryKey(), which takes the primary−key class as its argument and then returns the same primary key if it can be found in the underlying data source. • All finder methods must throw FinderException in addition to any other exceptions that you may have. • Within the finder methods, you will need to make database connections and other processing requests. When these are called, they are logically separate from the create methods. It is entirely possible that one of your find methods will be called before the create method, as the EJB server might request that an unused pooled bean service some of the search requests from clients. When you're deciding what finder methods to create, the best tip is to look at your list of ejbCreate() options. If you can create a bean based on that information, then surely someone will want to look up key information Chapter 16: Introducing Enterprise JavaBeans 355 using the same items? Of course this isn't always true. Consider the call−center application again: When searching for a user who has just phoned in, you might have nothing more than a user's real name and phone number or state. This information may not be unique, but it can give you a list of primary keys with which to find the matching users. However, the create < → find equivalence is a good starting point. Bearing this in mind, the customer−entity bean is going to have two finder methods — the compulsory one, and the other that uses the customer's name. public CustomerID ejbFindByPrimaryKey(CustomerID pk) throws EJBException, FinderException { } public Collection ejbFindWithName(String name) throws EJBException, FinderException { } One variation that you might be interested in applying here is a "find all" method that allows you to list the primary key of everyone in the database. This may or may not be convenient, depending on your application needs. The return type of finder methods is important. Because the container uses the return type to decide how to process the primary key, there are only certain classes you can use. For single object finders, such as findByPrimaryKey(), only the primary key type can be used. If you are writing a finder method that returns a number of primary keys, you have two options — java.util.Collection or java.util.Enumeration. Ideally, you should only use Collection as the return type. Enumeration is only used if you need to provide backward compatibility with old JDK and J2EE specification servers. Considering that you will be using the features of EJB 2.0 and, by implication, J2SE 1.3, then this should not be an issue for you. Writing the create methods Enough discussion of method names! Time to move on to writing the body of the methods. First let's deal with the ejbCreate() methods. They define the sort of data you need to store internally as class variables. Note The EJB specification says that the internal variables of the class should not be initialized until after the ejbCreate() method has been called. Your code should only set the internal variables from information provided in the parameters to the ejbCreate() method. Any other internal state, you should only set as the result of the various business methods. The idea is that the bean user will then fill in the rest of the data that were not provided through the ejbCreate() through the various business methods. For example, if you only provide a user name for the customer, you should not provide a default address, but instead wait for the setAddress() business method to be called. Many parts of the entity−bean internals will be familiar to you. For a start, you have a database, so you will need to create and access the appropriate driver instance. Then you will need to obtain a connection to the database and make the requests to obtain the data. You also need to decide how to deal with the database and its data. If you have a connection and the bean is coming and going from the pool, what is the best time to fetch an instance of Connection or Statement? Remember that you also have passivation issues to deal with, as well as the finder methods. The answer to this question is programmer−specific. Beans are long−lived, so once you've accessed a resource you can confidently keep everything around for later requests. Our personal preference is to create connections and statements as soon as possible, such as in the setEntityContext() method. However, if you Chapter 16: Introducing Enterprise JavaBeans 356 [...]... writing the Enterprise JavaBean code All that is left to do is create an application that will use the bean 369 Chapter 16: Introducing Enterprise JavaBeans Using Enterprise Beans on the Client Side Using EJBs in client code does not require the large amounts of coding that you've seen so far In fact, using them in any application is a breeze and one of the seductive aspects of using the J2EE environment... rs = stmt.executeQuery(); if(!rs.next()) throw new EJBException("User ID no known: " + key.id); 3 62 Chapter 16: Introducing Enterprise JavaBeans customerId = key.id; address = rs.getString (2) ; emailAddress = rs.getString(3); country = rs.getString(4); userName = rs.getString(5); phoneNumber = rs.getString (6) ; } catch(SQLException se) { throw new EJBException("DB fetch error: ", se); } } That's all there... instance from scratch, causing you to need a collection of method calls 366 Chapter 16: Introducing Enterprise JavaBeans Filling in the missing spaces You've seen how to create a remote and home interface, as well as how to write bean implementations, but how do the interfaces talk with the bean implementation? Ah, trade secret! The J2EE specification does not specify how this communication works, only... Inc.//DTD Enterprise JavaBeans 1.1//EN" "http:/ /java. sun.com/j2ee/dtds/ejb−jar _2_ 0.dtd"> Next, you place the opening tag, as defined by the preceding declaration Inside that tag, you start by listing descriptions and the list of beans included in this JAR file The DTD definition of the ejb−jar element is as follows: enterprise beans,... stmt.setInt(0, key.id); ResultSet rs = stmt.executeQuery(); if(!rs.next()) 360 Chapter 16: Introducing Enterprise JavaBeans throw new EJBException("User ID not known: " + key.id); customerId = key.id; address = rs.getString (2) ; emailAddress = rs.getString(3); country = rs.getString(4); userName = rs.getString(5); phoneNumber = rs.getString (6) ; } catch(SQLException se) { throw new EJBException("DB fetch error:... Container 368 Chapter 16: Introducing Enterprise JavaBeans Customer CustomerHome Customer CustomerEntityBean Bean CustomerID True < /enterprise beans> Tip All the items inside... will be 367 Chapter 16: Introducing Enterprise JavaBeans • Web client archive — When you use servlets or JSPs, they will be placed into a file called a Web ARchive or WAR file This is just a JAR file with a few extras: It keeps all the Web pieces of the application, such as HTML files, images, and so on • Application archive — Wrapping all these other files into a single deployable unit is the Enterprise. .. 375 Chapter 16: Introducing Enterprise JavaBeans That completes the code you need in order to integrate a JSP and EJB into the one action Simply deploy the code according to your J2EE environment tools, and you're up and running Using beans in JavaServer Pages with custom tags An alternate way of using EJBs within a JSP... management of the bean Just how does it fit in the middle? After all, you already have the remote interface and a bean that implements all the methods from the home interface: Just what use 363 Chapter 16: Introducing Enterprise JavaBeans is another interface going to be? Options for Storing and Loading Data in Entity Beans The EJB specification provides you with a lot of flexibility about how and when you store... starts with this step The only difference in the declarations is in the number of extra methods that must be added by your derived interface that are required by a particular bean type 364 Chapter 16: Introducing Enterprise JavaBeans The EJBHome interface is really simple, as only four methods are defined: two to access information about the home interface itself, and two to remove the bean Throughout this . EJBException("User ID no known: " + key.id); Chapter 16: Introducing Enterprise JavaBeans 3 62 customerId = key.id; address = rs.getString (2) ; emailAddress = rs.getString(3); country = rs.getString(4); . if(!rs.next()) Chapter 16: Introducing Enterprise JavaBeans 360 throw new EJBException("User ID not known: " + key.id); customerId = key.id; address = rs.getString (2) ; emailAddress. complete instance from scratch, causing you to need a collection of method calls. Chapter 16: Introducing Enterprise JavaBeans 366