| <?xml version="1.0" encoding="ISO-8859-1" ?> |
| <!-- |
| ~ Licensed to the Apache Software Foundation (ASF) under one |
| ~ or more contributor license agreements. See the NOTICE file |
| ~ distributed with this work for additional information |
| ~ regarding copyright ownership. The ASF licenses this file |
| ~ to you under the Apache License, Version 2.0 (the |
| ~ "License"); you may not use this file except in compliance |
| ~ with the License. You may obtain a copy of the License at |
| ~ |
| ~ http://www.apache.org/licenses/LICENSE-2.0 |
| ~ |
| ~ Unless required by applicable law or agreed to in writing, |
| ~ software distributed under the License is distributed on an |
| ~ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY |
| ~ KIND, either express or implied. See the License for the |
| ~ specific language governing permissions and limitations |
| ~ under the License. |
| --> |
| |
| <document> |
| <properties> |
| <title>Apache Synapse - Sample 471</title> |
| </properties> |
| <body> |
| <section name="Sample 471: Introduction to the EJB Mediator II - Invoking Stateful Session Beans"> |
| <div class="xmlConf"><definitions> |
| <proxy name="BuyAllProxy" transports="https http" startOnLoad="true" trace="disable"> |
| <target> |
| <!-- Iterate over all items in the request and call addItem() on the ShoppingCart EJB for each item. --> |
| <inSequence> |
| <property name="SESSION_ID" expression="get-property('MessageID')"/> |
| <iterate xmlns:m0="http://services.samples" preservePayload="false" |
| expression="//m0:buyItems/m0:items/m0:item"> |
| <target> |
| <sequence> |
| <ejb class="samples.ejb.ShoppingCart" beanstalk="demo" method="addItem" sessionId="{get-property('SESSION_ID')}" jndiName="ShoppingCartBean/remote"> |
| <args> |
| <arg value="{//m:item//m:id}" xmlns:m="http://services.samples"/> |
| <arg value="{//m:item//m:quantity}" xmlns:m="http://services.samples"/> |
| </args> |
| </ejb> |
| <sequence key="collector"/> |
| </sequence> |
| </target> |
| </iterate> |
| </inSequence> |
| </target> |
| </proxy> |
| |
| <!-- Prepare the response once all addItem() calls are finished. --> |
| <sequence name="collector"> |
| <aggregate> |
| <onComplete> |
| <ejb class="samples.ejb.ShoppingCart" beanstalk="demo" method="getItemCount" sessionId="{get-property('SESSION_ID')}" target="ITEM_COUNT"/> |
| <ejb class="samples.ejb.ShoppingCart" beanstalk="demo" method="getTotal" sessionId="{get-property('SESSION_ID')}" target="TOTAL" remove="true"/> |
| <payloadFactory> |
| <format> |
| <buyAllResponse xmlns=""> |
| <itemCount>$1</itemCount> |
| <total>$2</total> |
| </buyAllResponse> |
| </format> |
| <args> |
| <arg expression="get-property('ITEM_COUNT')"/> |
| <arg expression="get-property('TOTAL')"/> |
| </args> |
| </payloadFactory> |
| <respond/> |
| </onComplete> |
| </aggregate> |
| </sequence> |
| |
| </definitions></div> |
| <subsection name="Objective"> |
| <p> |
| Demonstrate the usage of the EJB mediator for invoking EJB Stateful |
| Session Beans hosted on a remote EJB Container. |
| </p> |
| </subsection> |
| <subsection name="Pre-requisites"> |
| <p> |
| <ul> |
| <li> |
| Follow steps 1 to 5 in <a href="sample470.html">Sample 470</a> to host the EJBs |
| in an EJB Container of your choice and to configure the <i>demo</i> beanstalk. |
| </li> |
| <li> |
| If the JNDI names assigned to the EJBs by your EJB Container differ from |
| the JNDI names specified in the sample 471 configuration file |
| (repository/conf/sample/synapse_sample_471.xml), edit the <i>jndiName</i> |
| attribute of all < ejb /> mediator invocations in the |
| <i>synapse_sample_471.xml</i> accordingly. |
| </li> |
| <li> |
| Start Synapse using the configuration numbered 471 |
| (repository/conf/sample/synapse_sample_471.xml): |
| <div class="command"> |
| Unix/Linux: sh synapse.sh -sample 471<br/> |
| Windows: synapse.bat -sample 471 |
| </div> |
| </li> |
| </ul> |
| </p> |
| </subsection> |
| <subsection name="Executing the Client"> |
| <p> |
| Send the following request to http://localhost:8280/services/BuyAllProxy |
| using a tool such at <a href="http://ws.apache.org/tcpmon/">TCPMon</a> or curl. |
| </p> |
| <div class="xmlConf"><soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/"> |
| <soapenv:Body> |
| <buyItems xmlns="http://services.samples"> |
| <items> |
| <item> |
| <id>2150</id> |
| <quantity>1</quantity> |
| </item> |
| <item> |
| <id>1189</id> |
| <quantity>2</quantity> |
| </item> |
| <item> |
| <id>890</id> |
| <quantity>4</quantity> |
| </item> |
| </items> |
| </buyItems> |
| </soapenv:Body> |
| </soapenv:Envelope></div> |
| |
| <p> |
| Each instance of the <i>ShoppingCart</i> stateful session bean hosted on the remote EJB container |
| maintains a state which keeps track of the number and the total price of the items |
| added via its <i>addItem(String itemId, int count)</i> method. The <i>float getTotal()</i> and |
| <i>int getItemCount()</i> methods are used to retrieve this state. |
| </p> |
| <p> |
| When the <i>BuyAllProxy</i> receives the above request, it iterates over all <item> elements |
| in the request and calls the <i>addItem()</i> method on the <i>ShoppingCart</i> bean, |
| once per each <item>, using the EJB mediator. Since the <i>sessionId</i> used for these |
| invocations is actually the message ID, each request works on a new <i>ShoppingCart</i> instance |
| which is created at the first EJB mediator invocation in that request's flow. |
| </p> |
| <p> |
| When all <i>addItem()</i> method calls are finished, <i>getItemCount()</i> and <i>getTotal()</i> methods |
| are invoked on the same <i>ShoppingCart</i> instance within the <i>collector</i> sequence and |
| results are stored in two message context properties named <i>ITEM_COUNT</i> and <i>TOTAL</i>. |
| The last EJB call on the shopping cart sets the EJB mediator attribute <i>remove = "true"</i> |
| instructing the current stateful bean stub to be removed from the beanstalk. This is because the |
| same stateful bean instance will not be used again (each request uses a new bean instance). If the |
| user does not explicitly remove the stub using this attribute, it will be removed automatically |
| upon timeout as specified by the beanstalk configuration. |
| </p> |
| <p> |
| Finally, the PayloadFactory mediator is used to build the response message which is sent back to the |
| client. |
| </p> |
| <p>A sample response is shown below.</p> |
| |
| <div class="xmlConf"><?xml version="1.0" encoding="UTF-8"?> |
| <soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/"> |
| <soapenv:Body> |
| <buyAllResponse> |
| <itemCount>7</itemCount> |
| <total>807.0</total> |
| </buyAllResponse> |
| </soapenv:Body> |
| </soapenv:Envelope></div> |
| </subsection> |
| </section> |
| <p><a href="../samples.html">Back to Catalog</a></p> |
| </body> |
| </document> |