📄 jms7.html
字号:
To create a new instance of a message-driven bean, the container instantiates the bean and then</p><div class="pSmartList1"><ul class="pSmartList1"><a name="wp82213"> </a><div class="pSmartList1"><li>Calls the <code class="cCode">setMessageDrivenContext</code> method to pass the context object to the instance</li></div><a name="wp82214"> </a><div class="pSmartList1"><li>Calls the instance's <code class="cCode">ejbCreate</code> method</li></div></ul></div><a name="wp82218"> </a><p class="pBody"><a href="JMS7.html#wp82228">Figure 29-10</a> shows the life cycle of a message-driven bean.</p><div align="left"><img src="images/Fig1310.gif" height="221" width="307" alt="Life Cycle of a Message-Driven Bean" border="0" hspace="0" vspace="0"/></div><p class="pBody"></p><p> <a name="82228"> </a><strong><font >Figure 29-10 Life Cycle of a Message-Driven Bean</font></strong></p><a name="wp92011"> </a><h3 class="pHeading2">Managing Distributed Transactions</h3><a name="wp82229"> </a><p class="pBody">JMS client applications use JMS API local transactions, described in <a href="JMS6.html#wp92878">Using JMS API Local Transactions</a>, which allow the grouping of sends and receives within a specific JMS session. J2EE applications commonly use distributed transactions in order to ensure the integrity of accesses to external resources. For example, distributed transactions allow multiple applications to perform atomic updates on the same database, and they allow a single application to perform atomic updates on multiple databases. </p><a name="wp82236"> </a><p class="pBody">In a J2EE application that uses the JMS API, you can use transactions to combine message sends or receives with database updates and other resource manager operations. You can access resources from multiple application components within a single transaction. For example, a servlet may start a transaction, access multiple databases, invoke an enterprise bean that sends a JMS message, invoke another enterprise bean that modifies an EIS system using the Connector architecture, and finally commit the transaction. Your application cannot, however, both send a JMS message and receive a reply to it within the same transaction; the restriction described in <a href="JMS6.html#wp92878">Using JMS API Local Transactions</a> still applies.</p><a name="wp82243"> </a><p class="pBody">Distributed transactions can be either of two kinds:</p><div class="pSmartList1"><ul class="pSmartList1"><a name="wp82246"> </a><div class="pSmartList1"><li><b class="cBold">Container-managed transactions.</b> The EJB container controls the integrity of your transactions without your having to call <code class="cCode">commit</code> or <code class="cCode">rollback</code>. Container-managed transactions are recommended for J2EE applications that use the JMS API. You can specify appropriate transaction attributes for your enterprise bean methods. </li></div><a name="wp82247"> </a><p class="pBodyRelative">Use the <code class="cCode">Required</code> transaction attribute to ensure that a method is always part of a transaction. If a transaction is in progress when the method is called, the method will be part of that transaction; if not, a new transaction will be started before the method is called and will be committed when the method returns.</p><a name="wp82251"> </a><div class="pSmartList1"><li><b class="cBold">Bean-managed transactions.</b> You can use these in conjunction with the<code class="cCode"> javax.transaction.UserTransaction</code> interface, which provides its own <code class="cCode">commit</code> and <code class="cCode">rollback</code> methods that you can use to delimit transaction boundaries. Bean-managed transactions are recommended only for those experienced in programming transactions.</li></div></ul></div><a name="wp82252"> </a><p class="pBody">You can use either container-managed transactions or bean-managed transactions with message-driven beans. </p><a name="wp82253"> </a><p class="pBody">To ensure that all messages are received and handled within the context of a transaction, use container-managed transactions and specify the <code class="cCode">Required</code> transaction attribute for the <code class="cCode">onMessage</code> method. This means that if there is no transaction in progress, a new transaction will be started before the method is called and will be committed when the method returns.</p><a name="wp82254"> </a><p class="pBody">When you use container-managed transactions, you can call the following <code class="cCode">MessageDrivenContext</code> methods:</p><div class="pSmartList1"><ul class="pSmartList1"><a name="wp82256"> </a><div class="pSmartList1"><li><code class="cCode">setRollbackOnly</code>. Use this method for error handling. If an exception occurs, <code class="cCode">setRollbackOnly</code> marks the current transaction so that the only possible outcome of the transaction is a rollback.</li></div><a name="wp82258"> </a><div class="pSmartList1"><li><code class="cCode">getRollbackOnly</code>. Use this method to test whether the current transaction has been marked for rollback.</li></div></ul></div><a name="wp82259"> </a><p class="pBody">If you use bean-managed transactions, the delivery of a message to the <code class="cCode">onMessage</code> method takes place outside of the distributed transaction context. The transaction begins when you call the <code class="cCode">UserTransaction.begin</code> method within the <code class="cCode">onMessage</code> method and ends when you call <code class="cCode">UserTransaction.commit</code>. Any call to the <code class="cCode">Connection.createSession</code> method must take place within the transaction. If you call <code class="cCode">UserTransaction.rollback</code>, the message is not redelivered, whereas calling <code class="cCode">setRollbackOnly</code> for container-managed transactions does cause a message to be redelivered.</p><a name="wp82260"> </a><p class="pBody">Neither the JMS API Specification nor the Enterprise JavaBeans Specification (available from <code class="cCode"><a href="http://java.sun.com/products/ejb/" target="_blank">http://java.sun.com/products/ejb/</a></code>) specifies how to handle calls to JMS API methods outside transaction boundaries. The Enterprise JavaBeans Specification does state that the EJB container is responsible for acknowledging a message that is successfully processed by the <code class="cCode">onMessage</code> method of a message-driven bean that uses bean-managed transactions. Using bean-managed transactions allows you to process the message by using more than one transaction or to have some parts of the message processing take place outside a transaction context. In most cases, however, container-managed transactions provide greater reliability and are therefore preferable.</p><a name="wp82261"> </a><p class="pBody">When you create a session in an enterprise bean, the container ignores the arguments you specify, because it manages all transactional properties for enterprise beans. It is still a good idea to specify arguments of <code class="cCode">true</code> and <code class="cCode">0</code> to the <code class="cCode">createSession</code> method to make this situation clear:</p><div class="pPreformattedRelative"><pre class="pPreformattedRelative">session = connection.createSession(true, 0);<a name="wp82262"> </a></pre></div><a name="wp82265"> </a><p class="pBody">When you use container-managed transactions, you usually specify the <code class="cCode">Required</code> transaction attribute for your enterprise bean's business methods.</p><a name="wp82266"> </a><p class="pBody">You do not specify a message acknowledgment mode when you create a message-driven bean that uses container-managed transactions. The container acknowledges the message automatically when it commits the transaction.</p><a name="wp82268"> </a><p class="pBody">If a message-driven bean uses bean-managed transactions, the message receipt cannot be part of the bean-managed transaction, so the container acknowledges the message outside of the transaction. When you package a message-driven bean using <code class="cCode">deploytool</code>, you use activation configuration properties to specify the acknowledgment mode. See <a href="JMS7.html#wp89569">Table 29-6 on page 1048</a> for details.</p><a name="wp82269"> </a><p class="pBody">If the <code class="cCode">onMessage</code> method throws a <code class="cCode">RuntimeException</code>, the container does not acknowledge processing the message. In that case, the JMS provider will redeliver the unacknowledged message in the future.</p><a name="wp82270"> </a><h3 class="pHeading2">Using the JMS API with Application Clients and Web Components</h3><a name="wp82271"> </a><p class="pBody">An application client can use the JMS API in much the same way a standalone client program does. It can produce messages, and it can consume messages by using either synchronous receives or message listeners. See Chapter <a href="MDB.html#wp79663">23</a> for an example of an application client that produces messages; see <a href="JMSJ2EEex3.html#wp79654">A J2EE Application that Uses the JMS API with an Entity Bean</a> and <a href="JMSJ2EEex5.html#wp79839">An Application Example that Deploys a Message-Driven Bean on Two J2EE Servers</a> for examples of using application clients to produce and to consume messages. </p><a name="wp82287"> </a><p class="pBody">The J2EE Platform Specification does not impose strict constraints on how Web components should use the JMS API. In the J2EE 1.4 Application Server, a Web component--one that uses either the Java Servlet API or JavaServerPages (JSP) technology--may send messages and consume them synchronously but may not consume them asynchronously. </p><a name="wp82288"> </a><p class="pBody">Because a blocking synchronous receive ties up server resources, it is not a good programming practice to use such a <code class="cCode">receive</code> call in a Web component. Instead, use a timed synchronous receive. For details about blocking and timed synchronous receives, see <a href="JMS5.html#wp79947">Writing the Client Programs</a>.</p><a name="wp78878"> </a><h3 class="pHeading2">Specifying Deployment Descriptors</h3><a name="wp90252"> </a><p class="pBody">When you package a J2EE application, you provide deployment descriptors for the application and its modules. This section describes the deployment descriptor elements specific to an application that uses the JMS API and message-driven beans. At release 1.4 of the J2EE platform, message-driven beans can be configured to consume messages from other messaging sources in addition to JMS providers.</p><a name="wp90272"> </a><p class="pBody">At release 1.4 of the J2EE platform, application servers must be able to support both DTDs and XML schemas. The order in which you specify elements in deployment descriptors is not significant when you use DTDs, but it is significant when you use XML schemas. Therefore, it is a good idea to use <code class="cCode">deploytool</code> to create the deployment descriptors for you.</p><a name="wp89788"> </a><p class="pBody">This section covers the following topics:</p><div class="pSmartList1"><ul class="pSmartList1"><a name="wp89791"> </a><div class="pSmartList1"><li>Deployment descriptor elements for connection factories and destinations</li></div><a name="wp89792"> </a><div class="pSmartList1"><li>Deployment descriptor elements for message-driven beans</li></div><a name="wp89797"> </a><div class="pSmartList1"><li>Deployment descriptor elements specified at run time</li></div><a name="wp89802"> </a><div class="pSmartList1"><li>Specifying activation configuration properties for message-driven beans</li></div></ul></div><a name="wp88591"> </a><h4 class="pHeading3">Deployment Descriptor Elements for Connection Factories and Destinations</h4><a name="wp89460"> </a><p class="pBody">Modules that send messages or receive messages synchronously use the elements listed in <a href="JMS7.html#wp88615">Table 29-3</a>. These elements describe the JMS resources referenced in module source code: connection factories and destinations. The XML Schema files used by the J2EE Application Server are in the directory <code class="cCode"><</code><code class="cVariable">J2EE_HOME</code><code class="cCode">>/lib/schemas/</code>.You use these elements in deployment descriptors for application clients, enterprise beans, and Web components. </p><div align="left"><table border="1" summary="Deployment Descriptor Elements for Connection Factories and Destinations" id="wp88615"> <caption><a name="wp88615"> </a><div class="pTableTitle">Table 29-3 Deployment Descriptor Elements for Connection Factories and Destinations</div></caption> <tr align="center"> <th><a name="wp88619"> </a><div class="pCellHeading">Element Name</div></th> <th><a name="wp88621"> </a><div class="pCellHeading">Description</div></th></tr> <tr align="left"> <td><a name="wp88623"> </a><div class="pCellBody"><code class="cCode"><resource-ref></code></div></td> <td><a name="wp88663"> </a><div class="pCellBody">Contains a declaration of the enterprise bean's reference to an external resource, such as a JMS API connection factory. Contains the elements <code class="cCode"><res-ref-name></code>, <code class="cCode"><res-type></code>, and <code class="cCode"><res-auth></code>. </div></td></tr> <tr align="left"> <td><a name="wp88627"> </a><div class="pCellBody"><code class="cCode"><res-ref-name></code></div></td> <td><a name="wp88722"> </a><div class="pCellBody">Specifies the coded name of a resource manager connection factory reference, such as <code class="cCode">jms/MyConnectionFactory</code>.</div></td></tr> <tr align="left"> <td><a name="wp88631"> </a><div class="pCellBody"><code class="cCode"><res-type></code></div></td> <td><a name="wp88633"> </a><div class="pCellBody">Specifies the type of the data source. The type is specified by the Java interface expected to be implemented by the connection factory. For JMS connection factories, the allowed interfaces are <code class="cCode">javax.jms.ConnectionFactory</code>, <code class="cCode">javax.jms.QueueConnectionFactory</code>, and <code class="cCode">javax.jms.TopicConnectionFactory</code>.</div></td></tr> <tr align="left"> <td><a name="wp88635"> </a><div class="pCellBody"><code class="cCode"><res-auth></code></div></td> <td><a name="wp88769"> </a><div class="pCellBody">Specifies whether the enterprise bean code signs on programmatically to the resource manager (<code class="cCode">Application</code>) or whether the Container will sign on to the resource manager on behalf of the bean. In the latter case, the Container uses information that is supplied by the Deployer. Normally, the value is <code class="cCode">Container</code>.</div></td></tr> <tr align="left"> <td><a name="wp88639"> </a><div class="pCellBody"><code class="cCode"><res-sharing-scope></code></div></td> <td><a name="wp88851"> </a><div class="pCellBody">Specifies whether connections obtained through the given resource manager connection factory reference can be shared. Normally, the value is <code class="cCode">Shareable</code>.</div></td></tr> <tr align="left"> <td><a name="wp88643"> </a><div class="pCellBody"><code class="cCode"><message-destination-ref></code></div></td> <td><a name="wp88920"> </a><div class="pCellBody">Specifies a reference to a message destination associated with a resource in the module's environment. Contains the elements <code class="cCode"><message-destination-ref-name></code>, <code class="cCode"><message-destination-type></code>, <code class="cCode"><message-destination-usage></code>, and <code class="cCode"><message-destination-link></code>. It is recommended that the <code class="cCode"><message-destination-ref></code> and <code class="cCode"><message-destination></code> elements be used instead of the <code class="cCode"><resource-env-ref></code> element that was introduced at release 1.3 of the J2EE platform.</div></td></tr> <tr align="left"> <td><a name="wp88647"> </a><div class="pCellBody"><code class="cCode"><message-destination-ref-name></code></div></td>
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -