Oracle9i Enterprise JavaBeans Developer's Guide and Reference Release 1 (9.0.1) Part Number A90188-01 |
|
To deploy your Enterprise JavaBean component into the database, you must provide the appropriate deployment descriptors. There are two possible deployment descriptors. Both deployment descriptors are written using XML notation. The format designated for all elements within each deployment descriptor are specified within a DTD file. Note that each item within the element must be specified within your deployment descriptors in the same order as it is defined in the DTD.
The following table describes both deployment descriptors:
This appendix briefly describes the sections within both of the deployment descriptors. For more information on the Sun Microsystems's XML deployment descriptor, see the "Deployment Descriptor" chapter in the Enterprise Javabeans 1.1 specification located at http://www.javasoft.com
. For more information on the Oracle-specific deployment descriptor, see "DTD for Oracle-Specific Deployment Descriptor".
This is the main deployment descriptor that contains most of the information about the bean: the bean identification, security roles, transaction demarcation, and any optional environment definition.
The following is the required header for all Oracle9i EJB deployment descriptors. It details the XML version and the XML DTD file, which details the syntax required for the descriptor.
<?xml version="1.0"?>
The following uses the DTD stored locally:
<!DOCTYPE ejb-jar PUBLIC "-//Sun Microsystems Inc.//DTD Enterprise JavaBeans 1.1 //EN" "ejb-jar.dtd">
However, you can retrieve the DTD remotely from Sun Microsystems through an HTTP URL, as shown below:
<!DOCTYPE ejb-jar PUBLIC "-//Sun Microsystems Inc.//DTD Enterprise JavaBeans 1.1 //EN" "http://java.sun.com/j2ee/dtds/ejb-jar_1_1.dtd">
When you deploy the bean and this deployment descriptor to the database, the Container will try to retrieve the DTD from the indicated website. However, the user that deploys the bean must also be granted SocketPermission
in order for the session to be created between the database session and the website. For example, if the user that is deploying the bean is SCOTT, and the deployment descriptor specifies the Sun Microsystems web site for retrieving the DTD, then before you can deploy, SCOTT must be granted SocketPermission
, as shown below:
call dbms_java.grant_permission('SCOTT',
'SYS:java.net.SocketPermission','java.sun.com:80','connect,resolve');
If another port number is specified within the <!DOCTYPE>
element, substitute that port number instead of the default 80.
The first element to be declared is the <ejb-jar>
element. Within this element, you define two sections: the <enterprise-beans>
section and the <assembly-descriptor>
section.
The overall structure for the EJB deployment descriptor follows this syntax:
<ejb-jar> //Start of JAR file descriptor <description> </description> //Description of JAR file <enterprise-beans> //EJB Descriptor section . . . </enterprise-beans> <assembly-descriptor> //Application Descriptor section . . . </assembly-descriptor> <ejb-client-jar> //specify output JAR file for ... //client stubs </ejb-client-jar> </ejb-jar>
The beans are described within the <enterprise-beans>
section. This section contains information such as the type of bean--entity or session, the home interface name, the remote interface name, the bean class name, and the type of persistence--container-managed or bean-managed. The following shows the elements contained within the <enterprise-beans>
section.
<enterprise-beans> //beginning of the EJB descriptor <entity> or <session> //define EJB type: entity or session <description> </description> //text display description <ejb-name> </ejb-name> //logical name for the bean <home> </home> //home interface name <remote> </remote> //remote interface name <ejb-class> </ejb-class> //bean class name <session-type> </session-type> //For session beans: Stateful always <persistence-type> </persistence-type> //For entity beans: container or //bean-managed? <prim-key-class> </prim-key-class> //For entity beans: primary key class <reentrant> </reentrant> //Reentrant boolean: True or False <cmp-field> </cmp-field> //Container-managed //fields for entity beans <primkey-field> </prim-key-field> //For entity beans: primary key field <transaction-type> </transaction-type> //transaction information for bean <env-entry> </env-entry> //bean environment definition <ejb-ref> </ejb-ref> //EJB environment definition <security-role-ref> </security-role-ref> //security role for bean <resource-ref> </resource-ref> //resource environment </session> or </entity> </enterprise-beans>
Each element is described in the following sections:
The first item you must define is whether the bean is a session or an entity bean. You do this with the <entity>
or <session>
element.
There are four names necessary to define the bean within the descriptor:
<home>
element.
<remote>
element.
<ejb-class>
element.
<ejb-name>
element. You can do one of two things with this element. You can declare the actual JNDI name within this element or you can define a logical name that identifies your bean within the deployment descriptor. Ultimately, the <ejb-name>
must resolve to the JNDI bound name for the bean. So, if you use a logical name, this name must be mapped to the JNDI name within the Oracle-specific deployment descriptor.
The following defines the purchase order bean as an entity bean with the following components:
purchase.PurchaseOrderHome
purchase.PurchaseOrder
purchaseServer.PurchaseOrderBean
/test/purchase
This example used the JNDI name, "
Note:
/test/purchase
", within the <ejb-name>
element. If a logical name had been used, such as PurchaseOrder
, then PurchaseOrder
would have to be mapped to "/test/purchase
" within the <mappings>
element in the Oracle-specific deployment descriptor. See "Defining Mappings" for more information.
<enterprise-beans><entity>
<description>no description</description><ejb-name>test/purchase</ejb-name>
<home>purchase.PurchaseOrderHome</home>
<remote>purchase.PurchaseOrder</remote>
<ejb-class>purchaseServer.PurchaseOrderBean</ejb-class>
<persistence-type>Container</persistence-type> <prim-key-class>java.lang.String</prim-key-class> <reentrant>False</reentrant></entity>
</enterprise-beans>
One element pertains only to session beans: the <session-type>
element. Since only stateful beans are supported, this element should always be defined as Stateful
. In fact, it defaults to Stateful
, so you do not need to specify this element.
<session> .... <session-type>Stateful</session-type> </session>
Certain elements define items that pertain only to entity beans. These are as follows:
<persistence-type>
element. Value can be either "Container
" or "Bean
".
<cmp-field>
element. Each data field is listed within its own <cmp-field>
<field-name>
section.
The primary key can be declared as a single field of a Java type that is consistent with SQL types, such as java.lang.String
or declared as a combination of several container-managed fields. The one restriction is that you cannot define the primary key to be a byte array that is mapped to a Long Raw column in the database.
Primary Key Declaration | Methodology Required |
---|---|
Java data type consistent with SQL types |
|
Combination of container-managed persistent fields for primary key |
In this example, the customer bean is a CMP entity bean with a customer number as its primary key and two persistent fields: customer name and address.
<persistence-type>
element.
custid
, which is declared as java.lang.String
.
<cmp-field>
elements as name
and addr
.
The method for translating the container-managed fields into actual persistent storage is dependent on the persistent manager that you choose. See "Defining Container-Managed Persistence" for more information.
Note:
<enterprise-beans> <entity> <description>customer bean</description> <ejb-name>/test/customer</ejb-name> <home>customer.CustomerHome</home> <remote>customer.Customer</remote> <ejb-class>customerServer.CustomerBean</ejb-class><persistence-type>Container</persistence-type>
<prim-key-class>java.lang.String</prim-key-class>
<reentrant>False</reentrant><cmp-field><field-name>custid</field-name></cmp-field>
<cmp-field><field-name>name</field-name></cmp-field>
<cmp-field><field-name>addr</field-name></cmp-field>
<primkey-field>custid</primkey-field>
</entity> </enterprise-beans>
In this example, the customer bean is a CMP entity bean with a complex primary key defined within its own serializable class. In addition, the CMP bean declares two persistent fields: customer name and address.
<persistence-type>
element.
customer.CustomerPK
class.
<cmp-field>
elements as name
and addr
.
The method for translating the container-managed fields into actual persistent storage is dependent on the persistent manager that you choose. See "Defining Container-Managed Persistence" for more information.
Note:
<enterprise-beans> <entity> <description>customer bean</description> <ejb-name>/test/customer</ejb-name> <home>customer.CustomerHome</home> <remote>customer.Customer</remote> <ejb-class>customerServer.CustomerBean</ejb-class><persistence-type>Container</persistence-type>
<prim-key-class>customer.CustomerPK</prim-key-class>
<reentrant>False</reentrant><cmp-field><field-name>custname</field-name></cmp-field>
<cmp-field><field-name>dobirth</field-name></cmp-field>
<cmp-field><field-name>name</field-name></cmp-field>
<cmp-field><field-name>addr</field-name></cmp-field>
</entity> </enterprise-beans>
The transaction, security, and reentrancy for the bean is defined by the following elements:
<reentrant>
element. Value should be either "True
" or "False
".
<transaction-type>
element. Value should be "Bean
" if the session bean uses bean demarcation or "Container
" if the session bean uses container demarcation for its transaction control.
Note that the transaction information--for both session and entity beans--is defined in more detail within the <assembly-descriptor>
section. See "Defining Transactions" for more information.
<security-role-ref>
element. This refers to a security role name used within the bean and should map to an actual security role defined within the <assembly-descriptor>
section. See "Defining Security" for more information.
The following example defines a customer bean that is not reentrant, uses bean-demarcated transactions, and uses the "CustRole
" logical name within the bean implementation when referring to its security role. This role name is mapped to SCOTT.
<enterprise-beans> <session> <ejb-name>CustomerBean</ejb-name> <home>customer.CustomerHome</home> <remote>customer.Customer</remote> <ejb-class>customerServer.CustomerBean</ejb-class><reentrant>False</reentrant>
<transaction-type>Bean</transaction-type>
<security-role-ref>
<role-name>CustRole</role-name>
<role-link>SCOTT</role-link>
</security-role-ref>
</session> </enterprise-beans>
You can create three types of environment elements that are accessible to your bean during runtime: environment variables, EJB references, and resource managers (JDBC DataSource
). These environment elements are static and can not be changed by the bean.
ISVs typically develop EJBs that are independent from the EJB container. In order to distance the bean implementation from the container specifics, you can create environment elements that map to one of the following: defined variables, entity beans, or resource managers. This indirection enables the bean developer to refer to existing variables, EJBs, and a JDBC DataSource
without specifying the actual name. These names are defined in the deployment descriptor and are linked to the actual names within the Oracle-specific deployment descriptor.
you can create environment variables that your bean can access through a lookup on the InitialContext
. These variables are defined within an <env-entry>
element and can be of the following types: String
, Integer
, Boolean
, Double
, Byte
, Short
, Long
, and Float
. The name of the environment variable is defined within <env-entry-name>
, the type is defined in <env-entry-type>
, and its initialized value is defined in <env-entry-value>
. The <env-entry-name>
is relative to the "java:comp/env"
context.
For example, the following two environment variables are declared within the XML deployment descriptor for java:comp/env/minBalance
and java:comp/env/maxCreditBalance
.
<env-entry> <env-entry-name>minBalance</env-entry-name> <env-entry-type>java.lang.Integer</env-entry-type> <env-entry-value>500</env-entry-value> </env-entry> <env-entry> <env-entry-name>maxCreditBalance</env-entry-name> <env-entry-type>java.lang.Integer</env-entry-type> <env-entry-value>10000</env-entry-value> </env-entry>
Within the bean's code, you would access these environment variables through the InitialContext
, as follows:
InitialContext ic = new InitialContext(); Integer min = (Integer)ic.lookup("java:comp/env/minBalance"); Integer max = (Integer) ic.lookup("java:comp/env/maxCreditBalance"));
Notice that to retrieve the values of the environment variables, you prefix each environment element with "java:comp/env/
", which is the location that the container stored the environment variable.
You can define an environment reference to an EJB within the deployment descriptor. If your bean calls out to another bean, you can enable your bean to invoke the second bean using a reference defined within the deployment descriptors. You create a logical name within the EJB deployment descriptor, which is mapped to the real name of the bean within the Oracle deployment descriptor.
The deployejb
tool binds the EJB reference defined in the EJB deployment descriptor to the bean's home interface. This enables the target bean to be retrieved without the originating bean needing to know the exact JNDI name for the target. Either way, you use JNDI to retrieve the target bean's home interface. Once retrieved, the bean referenced by the returned EJB reference is instantiated in the same session.
Declaring the target bean as an environment reference provides a level of indirection: the originating bean can refer to the target bean with a logical name. This is useful when the target bean's JNDI name within the name space may be different depending on the operating environment.
To define an EJB within the environment, you provide the following:
ejb/
", such as "ejb/myEmployee
", and will be available within the "java:comp/env/ejb
" context.
Session
" or "Entity
".
As shown in Figure A-1, the logical name for the bean is mapped to the JNDI name by providing the same link name, "HelloWorldBean
", in both the <ejb-link>
in the EJB deployment descriptor and the <ejb-name>
within the <ejb-mapping>
element in the Oracle-specific deployment descriptor.
The following example defines a reference to the Hello
bean, as follows:
java:comp/env/ejb/HelloWorld
".
hello.HelloHome
; its remote interface is hello.Hello
.
HelloWorldBean
" name.
As shown in Figure A-1, the <ejb-link>
is mapped to <ejb-name>
within the <ejb-mapping>
element in the Oracle-specific deployment descriptor by providing the same logical name in both elements. The Oracle-specific deployment descriptor would have the following definition to map the logical bean name of "java:comp/env/ejb/HelloWorld
" to the JNDI URL "/test/myHello
".
Note: For more information on the Oracle-specific deployment descriptor, see "Oracle-Specific Deployment Descriptor". |
To invoke this bean from within your implementation, you use the <ejb-ref-name
> defined in the deployment descriptor. You prefix this name with "java:comp/env/ejb/
", which is where the container places the EJB references defined in the deployment descriptor.
InitialContext ic = new InitialContext(); HelloHome hh = (HelloHome)ic.lookup("java:comp/env/ejb/HelloWorld");
The resource manager connection factory references can include resource managers such as JMS, Java mail, URL, and JDBC DataSource
objects. In this release, there are three resource manager connection factories that Oracle9i supports: JDBC DataSource
, mail Session
, and URL
. Similar to the EJB references, you can access these objects from JNDI by creating an environment element for each object reference. However, these references can only be used for retrieving the object within the bean that defines these references. Each is fully described in the following sections:
You can access a database through JDBC either using the traditional method or by creating an environment element for a JDBC DataSource
. In order to create an environment element for your JDBC DataSource
, you must do the following:
DataSource
within the JNDI name space using the bindds
tool. Refer to the Oracle9i Java Tools Reference for full details on this tool.
<res-ref-name>
element in the EJB deployment descriptor. This name should always start with "jdbc
". In the bean code, the lookup of this reference is always prefaced by "java:comp/env/jdbc
".
java:comp/env/jdbc
" preface and the logical name defined in the EJB deployment descriptor.
As shown in Figure A-2, the JDBC DataSource
was bound to the JNDI name "test/OrderDataSource
". The logical name that the bean knows this resource as is "jdbc/OrderDB
". These names are mapped together within the Oracle-specific deployment descriptor. Thus, within the bean's implementation, the bean can retrieve the connection to OrderDataSource
by using the "java:comp/env/jdbc/OrderDB
" environment element.
The JDBC DataSource
environment element is defined with the following information:
The environment element is defined within the EJB deployment descriptor by providing the logical name, "jdbc/OrderDB
", its type of javax.sql.DataSource
, and the authenticator of "Application
".
The environment element of "jdbc/OrderDB
" is mapped to the JNDI bound name for the connection, "test/OrderDataSource
" within the Oracle-specific deployment descriptor.
Once deployed, the bean can retrieve the JDBC DataSource
as follows:
javax.sql.DataSource db; java.sql.Connection conn; . . . db = (javax.sql.DataSource) initCtx.lookup("java:comp/env/jdbc/OrderDB"); conn = db.getConnection();
You can create an environment element for a Java mail Session
object through the following:
javax.mail.Session
reference within the JNDI name space using the bindms
tool. Refer to the Oracle9i Java Tools Reference for full details on this tool.
<res-ref-name>
element in the EJB deployment descriptor. This name should always start with "mail
". In the bean code, the lookup of this reference is always prefaced by "java:comp/env/mail
".
java:comp/env/mail
" preface and the logical name defined in the EJB deployment descriptor.
As shown in Figure A-3, the Session
object was bound to the JNDI name "test/myMailSession
". The logical name that the bean knows this resource as is "mail/testMailSession
". These names are mapped together within the Oracle-specific deployment descriptor. Thus, within the bean's implementation, the bean can retrieve the connection to the bound Session
object by using the "java:comp/env/mail/testMailSession
" environment element.
This environment element is defined with the following information:
The environment element is defined within the EJB deployment descriptor by providing the logical name, "mail/testMailSession
", its type of javax.mail.Session
, and the authenticator of "Application
".
The environment element of "mail/testMailSession
" is mapped to the JNDI bound name for the connection, "test/myMailSession
" within the Oracle-specific deployment descriptor.
Once deployed, the bean can retrieve the Session
object reference as follows:
InitialContext ic = new InitialContext(); Session session = (Session) ic.lookup("java:comp/env/mail/testMailSession"); //The following uses the mail session object //Create a message object MimeMessage msg = new MimeMessage(session); //Construct an address array String mailTo = "whosit@oracle.com"; InternetAddress addr = new InternetAddress(mailto); InternetAddress addrs[] = new InternetAddress[1]; addrs[0] = addr; //set the message parameters msg.setRecipients(Message.RecipientType.TO, addrs); msg.setSubject("testSend()" + new Date()); msg.setContent(msgText, "text/plain"); //send the mail message Transport.send(msg);
You can create an environment element for a Java URL
object through the following:
java.net.URL
reference within the JNDI name space using the bindurl
tool. Refer to the Oracle9i Java Tools Reference for full details on this tool.
<res-ref-name>
element in the EJB deployment descriptor. This name should always start with "url
". In the bean code, the lookup of this reference is always prefaced by "java:comp/env/url
".
java:comp/env/url
" preface and the logical name defined in the EJB deployment descriptor.
As shown in Figure A-4, the URL
object was bound to the JNDI name "test/myURL
". The logical name that the bean knows this resource as is "url/testURL
". These names are mapped together within the Oracle-specific deployment descriptor. Thus, within the bean's implementation, the bean can retrieve the connection to the bound Session
object by using the "java:comp/env/url/testURL
" environment element.
This environment element is defined with the following information:
The environment element is defined within the EJB deployment descriptor by providing the logical name, "url/testURL
", its type of java.net.URL
, and the authenticator of "Application
".
The environment element of "url/testURL
" is mapped to the JNDI bound name for the connection, "test/myURL
" within the Oracle-specific deployment descriptor.
Once deployed, the bean can retrieve the URL
object reference as follows:
InitialContext ic = new InitialContext(); URL url = (URL) ic.lookup("java:comp/env/url/testURL"); //The following uses the URL object URLConection conn = url.openConnection();
The application assembler adds generic information about all of the beans in this descriptor in the <assembly-descriptor>
section. This section has the following structure:
<assembly-descriptor> <security-role> </security-role> <method-permission> </method-permission> <container-transaction> </container-transaction> </assembly-descriptor>
These sections describe the security and transaction attributes.
You can manage some of your security for the user and method permissions from within the deployment descriptor. If you do not specify any method permissions, the default is that no users are allowed access.
In addition, as shown in Figure A-5, you can use a logical name for a role within your bean implementation, and map this logical name to the correct database role or user. The mapping of the logical name to a database role is specified in the Oracle-specific deployment descriptor. See "Security Role" for more information.
If you use a logical name for a database role within your bean implementation for methods such as isCallerInRole
, you can map the logical name to an actual database role by doing the following:
<enterprise-beans>
section <security-role-ref>
element. For example, to define a role used within the purchase order example, you may have checked, within the bean's implementation, to see if the caller had authorization to sign a purchase order. Thus, the caller would have to be signed in under a correct role. In order for the bean to not need to be aware of database roles, you can check isCallerInRole
on a logical name, such as POMgr
, since only purchase order managers can sign off on the order. Thus, you would define the logical security role, POMgr within the <security-role-ref><role-name>
element within the <enterprise-beans>
section, as follows:
<enterprise-beans> ... <security-role-ref> <role-name>POMgr</role-name> <role-link>SCOTT</role-link> </security-role-ref> </enterprise-beans>
The <role-link>
element within the <security-role-ref>
element can be the actual database role, which is defined further within the <assembly-descriptor>
section. Alternatively, it can be another logical name, which is still defined more in the <assembly-descriptor>
section and is mapped to an actual database role within the Oracle-specific deployment descriptor.
PurchaseOrder
bean must have authorized itself as SCOTT. Note that PurchaseOrder
is the name declared in the <entity
| session><ejb-name>
element.
Thus, the following defines the role as SCOTT, the EJB as PurchaseOrder
, and all methods by denoting the '*' symbol.
<assembly-descriptor> <security-role> <description>Role needed purchase order authorization</description> <role-name>SCOTT</role-name> </security-role> <method-permission> <role-name>SCOTT</role-name> <method> <ejb-name>PurchaseOrder</ejb-name> <method-name>*</method-name> </method> </method-permission> ... </assembly-descriptor>
After performing both steps, you can refer to POMgr within the bean's implementation and the container translates POMgr to SCOTT.
The <method>
element is used to define one or more methods within an interface or implementation. According to the EJB specification, this definition can be of one of the following forms:
<method> <ejb-name>EJBNAME</ejb-name> <method-name>*</method-name> </method>
<method> <ejb-name>myBean</ejb-name> <method-name>myMethodInMyBean</method-name> </method>
<method> <ejb-name>myBean</ejb-name> <method-name>myMethod</method-name> <method-params> <method-param>javax.lang.String</method-param> <method-param>javax.lang.String</method-param>
<method-params> <method>
The parameters are the fully-qualified Java types of the method's input parameters. If the method has no input arguments, the <method-params
> element contains no elements. Arrays are specified by the array element's type, followed by one or more pair of square brackets, such as int
[][].
method-intf
> element, as follows:
<method> <ejb-name>EmployeeService</ejb-name> <method-intf>Remote</method-intf> <method-name>create</method-name> <method-params> <method-param>java.lang.String</method-param> <method-param>java.lang.String</method-param> </method-params> </method>
Defining the remote interface in the <method-intf
> element differentiates the create(String, String)
method defined in the remote interface from the create(String, String)
method defined in the home interface, which would be defined as follows:
<method> <ejb-name>EmployeeService</ejb-name> <method-intf>Home</method-intf> <method-name>create</method-name> <method-params> <method-param>java.lang.String</method-param> <method-param>java.lang.String</method-param> </method-params> </method>
Entity beans can only use container-managed transactions; session beans can use either bean-managed or container-managed transactions. If you have a session bean, you define whether it uses bean or container-managed transactions within the <enterprise-beans>
section with the <transaction-type>
element. Values should be either "Bean
" or "Container
". For example, the following defines a session bean as a bean-managed transactional bean:
<enterprise-beans> <session> . . . <transaction-type>Bean</transaction-type> </session> </enterprise-beans>
For container-managed beans, you define the how the container maintains the transactions for the bean through transaction attributes. The transaction attributes define in what situations to start a new transaction, to continue an existing transaction, and others. If you have a bean-managed bean, you do not define any of these attributes for the bean. However, if your bean-managed bean invokes another bean, the target bean can be either bean or container-managed. All container-managed transactional beans must have this attributed defined.
The transaction attributes are specified in the <trans-attribute> element and are detailed in Table A-1.
Table A-1 Transaction Attributes
You can define the transaction attributes on a whole bean or on an individual method within the bean. Each definition is contained within the <container-transaction>
element. If you are defining an attribute for the entire bean, you supply the bean name (the <ejb-name>
defined within the <session>
or <entity>
element) within the <container-transaction>
<method>
<ejb-name>
element.
The following example defines the following:
PurchaseOrder
bean must have a transaction (Required).
The methods can be specified exactly as within the <
Note:
method-permission
> element. See "Defining Security" for more information.
price
method within the PurchaseOrder
bean must always have a new transaction (RequiresNew).
<assembly-descriptor> ... <container-transaction> <method> <ejb-name>PurchaseOrder</ejb-name> <method-name>*</method-name> </method> <trans-attribute>Required
</trans-attribute> </container-transaction> <container-transaction> <method> <ejb-name>PurchaseOrder</ejb-name> <method-name>price</method-name> </method> <trans-attribute>RequiresNew
</trans-attribute> </container-transaction> . . . </assembly-descriptor>
Finally, there are some Oracle-specific features that you need to specify for your transaction, such as whether default enlistment should occur, whether two-phase commit is configured, and whether transaction branches are allowed. See "Defining Oracle-Specific Elements for Transactions" for more information.
One of the tasks that the deployejb
tool performs is to create a JAR file with the required stubs and skeletons, which is used by the client at execution time. Unless this JAR file name is specified in the <ejb-client-jar
> element in the XML deployment descriptor, the default name for this JAR file is <input_JARname>_generated.jar
. This JAR file must be included in the CLASSPATH
for client execution.
The following defines that deployejb should create the client's stubs and skeletons in myClient.jar:
<ejb-client-jar>myClient.jar</ejb-client-jar>
The Oracle-specific deployment descriptor is used for the following:
This deployment descriptor has the following structure:
<?xml version="1.0"?> <!DOCTYPE oracle-descriptor PUBLIC "-//Oracle Corporation//DTD Enterprise JavaBeans 1.1//EN" "oracle-ejb-jar.dtd"> <oracle-ejb-jar> <oracle-descriptor> <mappings> <ejb-mapping> </ejb-mapping> <resource-ref-mapping> </resource-ref-mapping> </mappings> <run-as> </run-as> <persistence-provider> </persistence-provider> <persistence-descriptor> </persistence-descriptor> </oracle-descriptor> </oracle-ejb-jar>
The following is the required header for all Oracle9i EJB deployment descriptors. It details the XML version and the XML DTD file.
<?xml version="1.0"?>
<!DOCTYPE oracle-descriptor PUBLIC "-//Oracle Corporation.//DTD Oracle 1.1//EN" "oracle-ejb-jar.dtd">
Each bean is further specified within its own <oracle-descriptor>
element. The bean name is identified within the <ejb-name>
element right after the <oracle-descriptor>
element. This is only necessary if there is more than one bean in the deployed JAR file. If no <ejb-name>
element is supplied, all values specified within the <oracle-descriptor>
apply to all beans within the JAR. If there is only a single bean in the JAR, all values are applied to that single bean.
To define multiple beans, each bean specifies its values within its own <oracle-descriptor>
element. The following example defines values for a JAR file that contains two beans: PurchaseOrder
and CustomerInfo
.
The following defines the logical name for beans: PurchaseOrder
and CustomerInfo
within the EJB deployment descriptor.
<enterprise-beans><entity>
<description>no description</description>
<ejb-name>PurchaseOrder</ejb-name>
<home>purchase.PurchaseOrderHome</home>
<remote>purchase.PurchaseOrder</remote>
<ejb-class>purchaseServer.PurchaseOrderBean</ejb-class>
<persistence-type>Bean</persistence-type>
<prim-key-class>java.lang.String</prim-key-class>
<reentrant>False</reentrant>
</entity>
<entity>
<description>no description</description>
<ejb-name>CustomerInfo</ejb-name>
<home>customer.CustomerHome</home>
<remote>customer.Customer</remote>
<ejb-class>customer.CustomerBean</ejb-class>
<persistence-type>Bean</persistence-type>
<prim-key-class>java.lang.String</prim-key-class>
<reentrant>False</reentrant>
</entity>
</enterprise-beans>
Both of these beans are further specified within the Oracle deployment descriptor, as follows:
<oracle-descriptor><ejb-name>PurchaseOrder</ejb-name>
<mappings> . . . </mappings> . . . </oracle-descriptor> <oracle-descriptor><ejb-name>CustomerInfo</ejb-name>
<mappings> <ejb-mapping> . . . </ejb-mapping> </mappings> . . . </oracle-descriptor> </oracle-ejb-jar>
You can map logical names used within the EJB deployment descriptor to actual names used within the Oracle9i database. The different names that can be mapped are as follows:
As described in "Bean Names", the bean name can be either a logical name or a JNDI name. If you defined a logical name, as demonstrated in the following example, you must map this name to the actual JNDI name within the <mappings>
section.
The following defines a logical name of PurchaseOrder
for the bean with in the EJB deployment descriptor.
<enterprise-beans><entity>
<description>no description</description>
<ejb-name>PurchaseOrder</ejb-name>
<home>purchase.PurchaseOrderHome</home>
<remote>purchase.PurchaseOrder</remote>
<ejb-class>purchaseServer.PurchaseOrderBean</ejb-class>
<persistence-type>Bean</persistence-type>
<prim-key-class>java.lang.String</prim-key-class>
<reentrant>False</reentrant>
</entity>
</enterprise-beans>
The PurchaseOrder
logical name is mapped to its JNDI name within the <mappings>
section within the Oracle-specific deployment descriptor. The following example shows how the bean name is defined in the <ejb-name>
element of the <ejb-mapping>
element and the corresponding JNDI name is defined in the <jndi-name>
element.
<oracle-descriptor> <mappings> <ejb-mapping><ejb-name>PurchaseOrder</ejb-name>
<jndi-name>/test/purchase</jndi-name>
</ejb-mapping> </mappings> . . . </oracle-descriptor>
The EJB reference mapping is described in "Environment References To Other Enterprise JavaBeans". The structure of the mapping is the same as the bean name, demonstrated in "Bean Name".
The JDBC DataSource
connection mapping is described in "Environment References To Resource Manager Connection Factory References". You map the JDBC DataSource to the bound JNDI name with the <resource-ref-mapping>
element, as follows:
<oracle-descriptor> <mappings> <resource-ref-mapping> <res-ref-name>jdbc/EmployeeAppDB</res-ref-name> <jndi-name>jdbc/OracleDataSource</jndi-name> </resource-ref-mapping> </mappings> ... </oracle-descriptor>
The <res-ref-name>
element contains the JDBC DataSource
defined in the EJB deployment descriptor. The <jndi-name>
element contains the JNDI name bound to the JDBC DataSource within the name space. This example maps the "jdbc:comp/env/jdbc/EmployeeAppDB
" environment name to the JNDI name "jdbc/OracleDataSource
".
If you defined a logical name for the <role-name>
within the <assembly-descriptor>
, this logical name must be mapped to an actual database role or user within the Oracle-specific deployment descriptor.
For example, you define a logical role of POMGR
for the role necessary for purchase order authorization within the <assembly-descriptor>
. The actual database role that is allowed to make this authorization is SCOTT
. The following would be the necessary mapping definition within the Oracle-specific deployment descriptor:
<mappings> <security-role-mapping> <security-role> <description>POMGR role mapping</description> <role-name>POMGR</role-name> </security-role> <oracle-role>SCOTT</oracle-role> </security-role-mapping> </mappings>
As shown in Figure A-6, the <role-name>
of POMGR
defined in the <assembly-descriptor><security-role><role-name>
is mapped to SCOTT
within the Oracle-specific deployment descriptor in the <security-role-mapping>
element.
There are three elements that you can further specify for your global transaction.
The following shows the elements necessary for these elements, which are contained within the <transaction-manager>
element in the Oracle-specific deployment descriptor.
<mappings> ... <transaction-manager> <jndi-name>...</jndi-name> <default-enlist>TRUE</default-enlist> <create-branches>FALSE</create-branches> </transaction-manager> </mappings>
The local resource can be an Oracle9i database or an Oracle9i Application Server middle-tier cache. Within a global transaction, you do want the Oracle9i database to be enlisted; you do not want the Oracle9i Application Server cache enlisted.
The Oracle9i Application Server cache is read-only. If it is enlisted in the global transaction, the transaction manager assumes that a two-phase commit is necessary. Since the default for this element is FALSE, you only need to specify the <default-enlist>
element to TRUE in each Oracle9i database.
<mappings> ... <transaction-manager> ... <default-enlist>TRUE</default-enlist> </transaction-manager> </mappings>
If you are using two-phase commit for your global transaction, you must provide the UserTransaction
object's JNDI name to the <transaction-manager>
element within the Oracle-specific deployment descriptor. The following example specifies the UserTransaction
object "/test/myUTFor2pc
":
<mappings> ... <transaction-manager> <jndi-name>/test/myUTFor2pc</jndi-name> ... </transaction-manager> </mappings>
According to the X/Open XA protocol, if you want to apply two or more updates to a single database, the transaction manager monitors each update--known as a unit-of-work--through branches.
The <create-branches>
element defines whether more than one unit of work can be performed on a single database. That is, if several separate updates are to be applied to a single database, this element must be set to true. If false, only a single unit of work is allowed per database within the global transaction.
You can specify that branches are allowed within the global transaction by specifying the <create-branches>
element to TRUE, as follows:
<mappings>
...
<transaction-manager>
...
<create-branches>TRUE</create-branches>
</transaction-manager>
</mappings>
The <run-as>
element is an EJB 1.0 element that Oracle still supports within the Oracle-specific deployment descriptor. You can define that a particular EJB will run under the specified identity with the <run-as>
element. There are three types of identity that you can specify for your bean. They are as follows:
The <method
> element specifies the methods that the <run-as
> definition applies to. It takes in the following definitions:
ejb-name
>: The logical name of the bean defined in the XML deployment descriptor.
method-name
>: The method name (* implies all methods) that this mode applies to within the bean. Note that you can override a multiple definition with a single definition. For example, if you define SPECIFIED_IDENTITY for all methods (*) within the bean are run as PUBLIC. You also define SPECIFIED_IDENTITY for a single method (checkClient
) to run as SCOTT. The checkClient
method runs under SCOTT; all other methods run under PUBLIC.
method-params
>: If you have more than one method of this name with overloaded parameters and you want the <run-as
> to apply to only one of them, specify the parameters within this element.
For example, the following defines that the price
method, which requires two String parameters, in the PurchaseOrder
EJB will always run as SCOTT when invoked.
<run-as> <description>no description</description> <mode>SPECIFIED_IDENTITY</mode> <security-role> <role-name>SCOTT</role-name> </security-role> <method> <ejb-name>PurchaseOrder</ejb-name> <method-name>price</method-name> <methodl-params> <method-param>java.lang.String<method-param> <method-param>java.lang.String<method-param> </method> </run-as>
If you have chosen to have the container manage the persistent variables for your entity bean, you need to provide the name of the persistence provider--you map each persistence provider to the container-managed persistent bean. This version supports the Oracle Persistence Service Interface Reference Implementation (PSI-RI) persistence manager. Using this manager requires that you must define the mappings of the persistent fields to the database.
The persistence provider controls the management of all container-managed fields. It defines how to map the fields within the bean to corresponding persistent storage. It also defines how to save and update these fields from the bean to the storage.
You define the Oracle PSI-RI persistence provider is defined within the <persistence-provider>
element. The following elements describe the persistence provider:
The following defines the Oracle PSI-RI persistence provider, which uses the local database--the default--for storing the persistence fields. The logical name is defined as "PSI-RI
" and the class called for persistence management is oracle.aurora.ejb.persistence.ocmp.OcmpEntityDeployer
.
<persistence-provider> <description> specifies a type of persistence manager </description> <persistence-name>psi-ri<
/persistence-name> <persistence-deployer>oracle.aurora.ejb.persistence.ocmp.OcmpEntityDeployer
</persistence-deployer> </persistence-provider>
The following defines the same persistence provider that uses a remote database to store the persistence fields. The "/test/empDatabase
" JTA DataSource
is defined in the following example as the remote persistence storage. This DataSource
was bound by bindds
with the -type jta
option.
<persistence-provider> <description> specifies a type of persistence manager </description> <persistence-name>psi-ri</persistence-name> <persistence-deployer>oracle.aurora.ejb.persistence.ocmp.OcmpEntityDeployer
</persistence-deployer><persistence-datasource>/test/empDatabase</persistence-datasource>
</persistence-provider>
The persistent fields were defined in the EJB deployment descriptor in the <cmp-field>
elements. Each of these <cmp-field>
elements need to be persistently managed by your provider. You define a single provider for all <cmp-field>
elements within a single bean through the <persistence-descriptor>
element. You define the provider for the bean through the combination of the logical names for the bean and for the provider within the <persistence-descriptor>
. These fields are as follows:
For example, to define that Oracle PSI-RI manages all persistent fields within the purchase order bean, you specify the logical bean name, PurchaseOrder
, and the logical persistence provider name, Oracle PSI-RI, within the following fields:
<persistence-descriptor> <ejb-name>PurchaseOrder
</ejb-name> <persistence-name>psi-ri<
/persistence-name> . . . </persistence-descriptor>
The Oracle PSI-RI maps the persistent data types to database rows. It uses SQL to update the persistent fields between the bean and the database. Each persistent data type is mapped to the Oracle SQLJ data types documented in the Oracle9i SQLJ Developer's Guide and Reference. The data type mapping is documented fully on Table 5-1, "Type Mappings for Supported Host Expression Types" on page 5-2. The only restrictions is that the following data types are not supported:
Java Type | Oracle Types Definition | Oracle Datatype | |
---|---|---|---|
SQLJ stream classes |
|||
Oracle extensions |
|||
Query result objects |
|||
If you decide to use PSI-RI, you must define the following within the <psi-ri>
element, which exists within the <persistence-descriptor>
.
For example, the following<psi-ri>
maps the customer bean persistence fields--primary key, customer name, and address--to the customers table within SCOTT's schema <persistence-descriptor> <ejb-name>PurchaseOrder
</ejb-name> <persistence-name>psi-ri<
/persistence-name> <psi-ri> <schema>SCOTT
</schema> <table>customers
</table> <attr-mapping> <field-name>custid
</field-name> <column-name>cust_id
</column-name> </attr-mapping> <attr-mapping> <field-name>name
</field-name> <column-name>cust_name
</column-name> </attr-mapping> <attr-mapping> <field-name>addr
</field-name> <column-name>cust_addr
</column-name> </attr-mapping> </psi-ri> </persistence-descriptor>
If the persistent fields that you define are objects, you can ask Oracle PSI-RI to serialize some or all fields defined as persistent into a single database column. This column must be defined as either long Raw or Raw.
You define the fields and the destination column within the <serialize-mapping>
element. The persistent fields are mapped either within the <attr-mapping>
or the <serialize-mapping>
elements, but not in both.
The following example serializes the customer bean persistent fields--customer name, and address--and save them into the custinfo
column. Normally, you would do this if you wanted to serialize an object.
<persistence-descriptor> <ejb-name>PurchaseOrder
</ejb-name> <persistence-name>psi-ri<
/persistence-name> <psi-ri> <schema>SCOTT
</schema> <table>customers
</table> <serialize-mapping> <field-name>name</field-name> <field-name>addr</field-name> <column-name>custinfo</column-name> </serialize-mapping> </psi-ri> </persistence-descriptor>
The following is the full example for defining container-managed persistence for the customer example.
<persistence-provider> <description>use the simple CMP provider</description> <persistence-name>psi-ri</persistence-name> <persistence-deployer>oracle.aurora.ejb.persistence.ocmp.OcmpEntityDeployer
</persistence-deployer> </persistence-provider> <persistence-descriptor> <ejb-name>customerbean</ejb-name> <persistence-name>psi-ri</persistence-name> <psi-ri> <schema>SCOTT</schema> <table>customers</table> <attr-mapping> <field-name>custid</field-name> <column-name>cust_id</column-name> </attr-mapping> <attr-mapping> <field-name>name</field-name> <column-name>cust_name</column-name> </attr-mapping> <attr-mapping> <field-name>addr</field-name> <column-name>cust_addr</column-name> </attr-mapping> </psi-ri> </persistence-descriptor> </oracle-descriptor>
<!-- This is the XML DTD for the Oracle Specific EJB deployment descriptor -->The oracle-ejb-jar element is the root element of the Oracle-specific deployment descriptor. It contains at least one oracle-descriptor. --> <!ELEMENToracle-ejb-jar
(oracle-descriptor+) <!-- Each oracle-descriptor element defines a single bean within the EJB JAR file. You must have an oracle-descriptor for each bean. This element contains the EJB name for the bean, an optional description, optional structural information about logical name mappings, optional definitions for run-as beans and/or methods, and definitions of container-managed persistence. --> <!ELEMENToracle-descriptor
(ejb-name?, mappings*, run-as*, persistence-provider*, persistence-descriptor*)> <!-- The ejb-name element defines the logical name for the bean that was used in the XML deployment descriptor --> <!ELEMENTejb-name
(#PCDATA)> <!-- The mappings section enables you to map logical names defined in the XML deployment descriptor to actual names. Bean logical names are mapped to JNDI names; security logical names are mapped to database roles or users. --> <!ELEMENTmappings
(ejb-mapping*, security-role-mapping*, resource-ref-mapping*, transaction-manager*)> <!-- The ejb-mapping element maps an EJB to its bound JNDI name --> <!ELEMENTejb-mapping
(ejb-name, jndi-name)> <!-- The security-role-mapping element maps security logical names to a database role or user --> <!ELEMENTsecurity-role-mapping
(security-role, oracle-role)> <!-- The resource-ref-mapping element maps any environment variable defined in the XML deployment descriptor to the JNDI name for the target object --> <!ELEMENTresource-ref-mapping
(res-ref-name, jndi-name)> <!-- The transaction manager defines the UserTransaction JNDI name that manages the global transaction. This is only required for transactions that use two-phase commit --> <!ELEMENTtransaction-manager
(description?, jndi-name?, default-enlist?,
create-branches?)> <!-- The jndi-name element specifies a JNDI name for a bound object --> <!ELEMENTjndi-name
(#PCDATA)> <!-- The default-enlist element defines whether a local resource is automatically enlisted in the global transaction. If TRUE, the resource is enlisted. The default is FALSE, which is useful in an iAS Cache environment. <!ELEMENTdefault-enlist
(#PCDATA)> <!-- The create-branches element defines whether branches are enabled in the global transaction
<!ELEMENTcreate-branches
(#PCDATA)> <!-- The run-as element enables you to specify a bean or certain methods within a bean to run with an identity other than its own. The modes allowed are CLIENT_IDENTITY (default), SYSTEM_IDENTITY, and SPECIFIED_IDENTITY. With the SPECIFIED_IDENTITY mode, you must provide the identity within the <security-role> element. --> <!ELEMENTrun-as
(description?, mode, security-role, method)> <!-- The mode element specifies the type of <run-as> identity. The values can be one of the following:SYSTEM_IDENTITY, SPECIFIED_IDENTITY, CLIENT_IDENTITY if mode is SPECIFIED_IDENTITY, security-role must be specified if mode is SYSTEM_IDENTITY or CLIENT_IDENTITY and security-role is specified, security-role is ignored --> <!ELEMENTmode
(#PCDATA)> <!-- The security-role element specifies a database role --> <!ELEMENTsecurity-role
(description?, role-name)> <!-- The role-name element specifies a database role or user --> <!ELEMENTrole-name
(#PCDATA)> <!-- The method element defines a method by the bean's logical name, optionally adding the interface name, the method name, and if overloading is present for this method, the parameters of the method you are indicating. --> <!ELEMENTmethod
(description?, ejb-name, method-intf?, method-name, method-params?)> <!--The method interface defines where the method is specified--> <!ELEMENTmethod-intf
(#PCDATA)> <!-- The method name element takes in the actual name of a method defined. --> <!ELEMENTmethod-name
(#PCDATA)> <!-- The method-params element specifies one or more parameters for a method. --> <!ELEMENTmethod-params
(method-param*)> <!-- The method-param defines a single parameter for a method by its class type--> <!ELEMENTmethod-param
(#PCDATA)> <!-- The oracle-role element specifies a database role or user --> <!ELEMENToracle-role
(#PCDATA)> <!-- The ejb-ref-name is the logical name for the EJB reference specified in the XML deployment descriptor --> <!ELEMENTejb-ref-name
(#PCDATA)> <!-- The res-ref-name element is the logical name for the resource reference specified in the XML deployment descriptor --> <!ELEMENTres-ref-name
(#PCDATA)> <!--- persistence-provider describes the container managed persistence --> <!-- The persistence-provider element specifies the CMP provider that you are using. At this time, only Oracle9i PSI-RI is supported. --> <!ELEMENTpersistence-provider
(description?, persistence-name, persistence-deployer, persistence-datasource?)> <!ELEMENTdescription
(#PCDATA)> <!-- The persistence-name element defines the name of the provider. For Oracle9i, this should be psi-ri --> <!ELEMENTpersistence-name
(#PCDATA)> <!-- The persistence-deployer is the class of the CMP provider. This should be oracle.aurora.ejb.persistence.ocmp.OcmpEntityDeployer. --> <!ELEMENTpersistence-deployer
(#PCDATA)> <!-- The JTA DataSource URL where the persistent information is written. -- The default is the local (KPRB) database. --> <!ELEMENTpersistence-datasource
(#PCDATA)> <!-- The persistence-descriptor element defines the persistence fields in the bean that must be managed by the CMP provider --> <!ELEMENTpersistence-descriptor
(description?, ejb-name, persistence-name, persistence-param*, psi-ri*)> <!ELEMENTpersistence-param
(#PCDATA)> <!-- The psi-ri element defines how the persistence fields int he beans are mapped to database tables and columns. --> <!ELEMENTpsi-ri
(schema, table, keepcase?, attr-mapping+, serialize-mapping?)> <!-- The schema element specifies the schema where the table exists --> <!ELEMENTschema
(#PCDATA)> <!-- The table element specifies the table where to store the persistent fields --> <!ELEMENTtable
(#PCDATA)> <!-- The attr-mapping element specifies how each persistent field is mapped to a corresponding column in the table --> <!ELEMENTattr-mapping
(field-name, column-name, keepcase?)> <!-- The keepcase element specifies whether all values specified within the parent element are case-sensitive. If true, all values are case-sensitive. If false, all values are upper-cased. Default is false. --> <!ELEMENT keepcase (#PCDATA)> <!-- If you serialize all persistent fields into a single column, use the serialize-mapping element --> <!ELEMENTserialize-mapping
(field-name+, column-name)> <!-- The field-name element specifies the persistent variable in the bean --> <!ELEMENTfield-name
(#PCDATA)> <!-- The column-name element specifies the column for a single persistent field --> <!ELEMENTcolumn-name
(#PCDATA)>
|
![]() Copyright © 1996-2001, Oracle Corporation. All Rights Reserved. |
|