Building the MedRec Applications

Tutorial 12: Invoking a Web Service from a Client Application

This tutorial describes how to invoke the MedRecWebServices WebLogic Web Service you created in Tutorial 11: Exposing a Stateless Session EJB as a Web Service from the following types of client applications:

- Stateless session EJB deployed to WebLogic Server
- Stand-alone Java Swing client application
- .NET client

Stateless session EJBs and stand-alone Java clients use the Web Service-specific client JAR file, generated by the clientgen Ant task, that contains most of the Java code you need to invoke a Web Service. The .NET client is written in C# and is provided to show that you can invoke a WebLogic Web Service from non-Java clients as well.

Note: You can use the clientgen Ant task to generate the JAX-RPC stubs for Web Services deployed on both WebLogic Server and other application servers.

The tutorial includes the following sections:

- Prerequisites
- Procedures
- Best Practices
- The Big Picture
- Related Reading

Prerequisites

It is assumed that you already know how to create a session EJB, a stand-alone Java Swing client application, and a .NET client application, and you want to learn how to update them to invoke a Web Service.

Before starting this tutorial, complete tutorials 5 through 11 to create the project directory and perform the intermediate build steps for the Physician and Medrec Applications. If you skipped any of the tutorials 5 through 11, you can catch up by following these steps:

1. Set your environment:

   >     c:\bea\user_projects\domains\MedRecDomain\setenv.cmd

2. Move to the c:\medrec_tutorial\src\physicianEar subdirectory and execute the ant command:

   >     cd c:\medrec_tutorial\src\physicianEar

   >     ant -f wlcompile_tutorial.xml

   >     ant -f wldeploy_tutorial.xml

3. Move to the c:\medrec_tutorial\src\medrecEar subdirectory and execute the ant command:

   >     cd c:\medrec_tutorial\src\medrecEar

   >     ant prepare build.split.dir

   >     ant -f webservices_tutorial.xml

   >     ant -f webservices_tutorial.xml deploy

   Note: In the XXX_tutorial.xml files, it is assumed that your MedRec project directory is c:\medrec_tutorial. If your project directory is different, you must update the files to ensure that they work correctly.

Procedures

The following procedures show the steps and code excerpts needed to invoke a Web Service from different types of client applications.

- Procedure 1: Invoke a Web Service from an EJB deployed on WebLogic Server.
- Procedure 2: Invoke a Web Service from a stand-alone Java Swing client application.
- Procedure 3: Invoke a Web Service from a .NET client.

Procedure 1: Invoke a Web Service from an EJB deployed on WebLogic Server.

This procedure describes how to invoke a Web Service from the PhysicianSessionEJB of the Physician application. The procedure shows you how to run the clientgen Ant task to generate most of the needed Java code into a client JAR file, then walks you through the code in the PhysicianSessionEJB used to invoke the Web Service.

1. Change to the physicianEar subdirectory of the MedRec project directory:

   >     cd c:\medrec_tutorial\src\physicianEar

2. Use your favorite text editor to create a file called my_webserv_client.xml file:

   >     notepad my_webserv_client.xml

3. Add the following lines to the my_webserv_client.xml file (substituting, if necessary, your actual MedRec project directory for c:/medrec_tutorial).

   Note: If you do not want to create the build file manually, copy the contents of the ws_ejb_client_tutorial.xml file to the new file, my_webserv_client.xml. Then follow along to understand the file contents. In the ws_ejb_client_tutorial.xml file, it is assumed that your MedRec project directory is c:/medrec_tutorial.

   >     <project name="EJB Web Service Invoke" default="build.ws.client">

   >       <target name="build.ws.client">

   >         <clientgen

   >           wsdl="http://localhost:7101/ws_medrec/MedRecWebServices?WSDL"

   >           packageName="com.bea.medrec.webservices"

   >           keepGenerated="false"

   >     clientjar="c:/medrec_tutorial/build/physicianEar/APP-INF/lib/webServicesEjb_cli
   >     ent.jar" />

   >       </target>

   >     </project>

   The Ant build file calls the clientgen Web Services Ant task which generates a client JAR file that contains most of the Java code (in particular, the JAX-RPC stubs) you need to invoke a Web Service. The wsdl attribute specifies that the clientgen Ant task should use the WSDL of the WebLogic Web Service you deployed in Tutorial 11: Exposing a Stateless Session EJB as a Web Service when generating the client JAR file. The JAR file, called webServicesEjb_client.jar, is created in the APP-INF/lib build directory of the Physician application, physicianEar.

   Note: In the preceding Ant build file, it is assumed that the MedRecWebServices WebLogic Web Service is deployed and its WSDL is accessible. If you have not yet deployed the Web Service, you can point the wsdl attribute to a static WSDL file, distributed as part of the MedRec tutorial JAR file. The static file is distributed as a convenience; typically you point clientgen to a dynamically generated WSDL to create the client JAR file. To use the static WSDL file, update the my_webserv_client.xml as shown in bold:

   >     <project name="EJB Web Service Invoke" default="build.ws.client">

   >       <target name="build.ws.client">

   >         <clientgen

   >           wsdl="c:/medrec_tutorial/dist/MedRecService.wsdl"

   >           packageName="com.bea.medrec.webservices"

   >           keepGenerated="false"

   >     clientjar="c:/medrec_tutorial/build/physicianEar/APP-INF/lib/webServicesEjb_cli
   >     ent.jar" />

   >       </target>

   >     </project>

4. Ensure you have set your environment using the MedRecDomain environment script:

   >     c:\bea\user_projects\domains\MedRecDomain\setEnv.cmd

5. Execute the clientgen Ant task by running the my_webserv_client.xml script:

   >     ant -f my_webserv_client.xml

   The clientgen Ant task shows the following output:

   >     Buildfile: my_webserv_client.xml

   >     build.ws.client:

   >     [clientgen] Generating client jar for
   >     http://localhost:7101/ws_medrec/MedRecWebServices?WSDL ...

   >     BUILD SUCCESSFUL

   >     Total time: 15 seconds

   The clientgen Ant task automatically generates the client JAR file into the APP-INF/lib directory of the physicianEar build directory, which means that the JAR file is automatically added to the EJB's CLASSPATH when the EJB is deployed in development mode to WebLogic Server.

   When you package the Physician application for production, package the Web Services client JAR file the same as any other supporting JAR files inside of the EJB JAR file.

6. Update the PhysicianSessionEJB to invoke the Web Service.

   Note: This part of the tutorial simply walks you through the EJB code you would write; the PhysicianSessionEJB.ejb code in the MedRec tutorial JAR file already contains the code needed to invoke the MedRecWebServices Web Service.

   1. Change to the directory that contains the PhysicianSessionEJB Java code:

   >     cd c:\medrec_tutorial\src\physicianEar\physSessionEjbs\com\bea\medrec\controller

   2. Open the PhysicianSessionEJB.ejb file in your favorite editor:

   >     notepad PhysicianSessionEJB.ejb

   3. Search for the private method getMedRecWebServicesPort(). This method contains the Java code that creates a JAX-RPC stub of the Web Service:

   >     wsdl_url = System.getProperty("phys.app.wsdl.url");

   >     logger.debug("Wsdl url: "+wsdl_url);

   >     MedRecWebServices service = new

   >            MedRecWebServices_Impl(wsdl_url);

   >     port = service.getMedRecWebServicesPort();

   The URL of the WSDL of the deployed MedRecWebServices is passed to the EJB using the phys.app.wsdl.url system property that was set in the MedRecServer startup script in the first tutorial, Tutorial 1: Creating a WebLogic Domain and Server Instance for Development. The value of the system property is the WSDL of the Web Service:

   >     http://localhost:7101/ws_medrec/MedRecWebServices?WSDL

   4. The public methods of PhysicianSessionEJB use this JAX-RPC stub to invoke Web Service operations.

   For example, search for the public method addRecord(). It contains the following Java code that invokes the addRecord operation of the MedRecWebServices Web Service:

   >     RecordWS recordWS = PhysicianClientUtils.toRecordWS(pRecord);

   >     port.addRecord(recordWS);

   The PhysicianClientUtils.toRecordWS() method is a utility that converts the standard Record Value object to a Web Service-specific RecordWS data type, to ensure interoperability. For details, see The Big Picture.

7. Compile and run PhysicianSessionEJB as usual.

   For information about compiling, see Tutorial 7: Compiling Applications Using the Split Development Directory.

Procedure 2: Invoke a Web Service from a stand-alone Java Swing client application.

This procedure shows how to invoke a Web Service from a stand-alone Java Swing client application. The procedure first describes how to run the clientgen Ant task to generate most of the needed Java code into a client JAR file and then walks you through the client code you need to write. It is assumed that you know how to write, compile, and run a Java Swing client application.

A stand-alone client application must update its CLASSPATH to include the client JAR file generated by the clientgen Ant task, as well as the runtime Web Services JAR file WL_HOME\server\lib\webserviceclient.jar, where WL_HOME refers to the top-level directory of WebLogic Platform.

1. Change to the clients subdirectory of the MedRec project directory:

   >     cd c:\medrec_tutorial\src\clients

2. Use your favorite text editor to create a file called my_webserv_client.xml file:

   >     notepad my_webserv_client.xml

3. Add the following lines to the my_webserv_client.xml file (substituting, if necessary, your actual MedRec project directory for c:/medrec_tutorial).

   Note: If you do not want to create the build file manually, copy the contents of the file ws_standalone_client_tutorial.xml file to the new file, my_webserv_client.xml. Then follow along to understand the file contents. It is assumed that your MedRec project directory is c:/medrec_tutorial.

   >     <project name="Standalone Web Service Invoke" default="build.ws.client" >

   >       <target name="build.ws.client">

   >         <clientgen

   >           wsdl="http://localhost:7101/ws_medrec/MedRecWebServices?WSDL"

   >           packageName="com.bea.medrec.webservices"

   >           keepGenerated="false"

   >           clientjar="c:/medrec_tutorial/build/clients/webServicesEjb_client.jar" />

   >       </target>

   >     </project>

   The Ant build file calls the clientgen Web Services Ant task which generates a client JAR file that contains most of the Java code (in particular, the JAX-RPC stubs) you need to invoke a Web Service. The wsdl attribute specifies that the clientgen Ant task should use the WSDL of the WebLogic Web Service you deployed in Tutorial 11: Exposing a Stateless Session EJB as a Web Service when generating the client JAR file. The JAR file, called webServicesEjb_client.jar, is created in the clients build directory.

   Note: In the preceding Ant build file, it is assumed that the MedRecWebServices WebLogic Web Service is deployed and its WSDL is accessible. If you have not yet deployed the Web Service, you can point the wsdl attribute to a static WSDL file, distributed as part of the MedRec tutorial JAR file. The static file is distributed as a convenience; typically you point clientgen to a dynamically generated WSDL to create the client JAR file. To use the static WSDL file, update the my_webserv_client.xml as shown in bold:

   >     <project name="Standalone Web Service Invoke" default="build.ws.client" >

   >       <target name="build.ws.client">

   >         <clientgen

   >           wsdl="c:/medrec_tutorial/dist/MedRecService.wsdl"

   >           packageName="com.bea.medrec.webservices"

   >           keepGenerated="false"

   >           clientjar="c:/medrec_tutorial/build/clients/webServicesEjb_client.jar" />

   >       </target>

   >     </project>

4. Ensure you have set your environment using the MedRecDomain environment script:

   >     c:\bea\user_projects\domains\MedRecDomain\setEnv.cmd

5. Execute the clientgen Ant task by running the my_webserv_client.xml script:

   >     ant -f my_webserv_client.xml

   The clientgen Ant task shows the following output:

   >     Buildfile: my_webserv_client.xml

   >     build.ws.client:

   >     [clientgen] Generating client jar for
   >     http://localhost:7101/ws_medrec/MedRecWebServices?WSDL ...

   >     BUILD SUCCESSFUL

   >     Total time: 14 seconds

6. Update the stand-alone Java Swing client application to invoke the Web Service.

   Note: This part of the tutorial simply walks you through the Java code you would write; the Java Swing client application of the MedRec tutorial JAR file already contains the code needed to invoke the MedRecWebServices Web Service.

   1. Change to the directory that contains the Java Swing client application code:

   >     cd c:\medrec_tutorial\src\clients\com\bea\medrec\webservices\swing

   2. Open the EditProfileFrame.java file in your favorite editor:

   >     notepad EditProfileFrame.java

   3. Search for the method submitButton_actionPerformed(ActionEvent e) which returns patient information, based on the patient's social security number, when a user of the application clicks Submit. This method contains the following Java code:

   >     MedRecWebServices ws = new

   >        MedRecWebServices_Impl(this.WSDLTextField.getText());

   >     MedRecWebServicesPort port  = ws.getMedRecWebServicesPort();

   >     PatientWS patientWS =

   >        (PatientWS)port.findPatientBySsn(this.patientIDTextField.getText());

   The preceding code shows how to create a JAX-RPC stub of the MedRecWebServices Web Service from the WSDL in the WSDLTextField of the application, and then invoke the findPatientBySsn Web Service operation.

   4. Search for the method saveButton_actionPerformed(ActionEvent e), which saves updated patient information to the MedRec application by invoking the updatePatient Web Service operation:

   >           PatientWS patientWS = Utils.toPatientWS(patient);

   >           port.updatePatient(patientWS);

   The Utils.toPatientWS() method is a utility that converts the standard Patient Value object to a Web Service-specific PatientWS data type, to ensure interoperability. For details, see The Big Picture.

7. Change to the main source directory for the client applications:

   >     cd c:\medrec_tutorial\src\clients

8. Compile the Java Swing application using ant with the existing build.xml file:

   >     ant -f build.xml compile.client

9. Run the application:

   >     ant -f build.xml run

10. In the application, enter a SSN number of 123456789 and click Submit; if the MedRec application is deployed and running correctly, you will see information returned about a patient. The command window from which you ran the application shows the SOAP request and response messages resulting from the Web Service operation invokes.

    When you run the stand-alone client application, make sure its CLASSPATH includes the client JAR file generated by the clientgen Ant task, as well as the runtime Web Services JAR file WL_HOME/server/lib/webserviceclient.jar, where WL_HOME refers to the top-level directory of WebLogic Platform.

Procedure 3: Invoke a Web Service from a .NET client.

You can also invoke the MedRecWebServices WebLogic Web Service from a .NET client application written in C#.

You must install the .NET Framework on your computer before you can create and run the .NET client. For details, see http://msdn.microsoft.com/netframework/downloads/howtoget.asp.

The sample .NET client that invokes the MedRecWebServices WebLogic Web service is in the following directory:

>     c:\medrec_tutorial\src\clients\CSharpClient

To run the client, execute the following file:

>     c:\medrec_tutorial\src\clients\CSharpClient\bin\Release\CSharpClient.exe

Best Practices

- When writing a Java client application to invoke a Web Service (either WebLogic or non-WebLogic), use the clientgen Ant task to generate the client JAR file that contains the JAX-RPC stubs for your Web Service. This client JAR file contains almost all the Java code you need to invoke a Web Service. Be sure to update the CLASSPATH of the client application with this JAR file.
- Stand-alone Java client applications also need to include the runtime client JAR file WL_HOME\server\lib\webserviceclient.jar in their CLASSPATH, where WL_HOME refers to the top-level directory of WebLogic Platform. This runtime JAR file contains the runtime implementation of JAX-RPC.
- Use the wsdl attribute of clientgen to generate the client JAR file from the WSDL, or public contract, of a Web Service.

The Big Picture

Client applications that invoke Web Services can be written using any technology: Java, Microsoft SOAP Toolkit, Microsoft .NET, and so on. Java client applications use the Java API for XML-Based RPC (JAX-RPC), a Sun Microsystems specification that defines the Java client API for invoking a Web Service. A Java client application can be an EJB deployed on WebLogic Server, or a stand-alone Java client.

In Tutorial 11: Exposing a Stateless Session EJB as a Web Service, you learned how to create and deploy the MedRecWebServices Web Service (part of the main MedRec application), which contains operations to find and update patient information, such as updatePatient and findPatientBySsn. The public contract of the Web Service is published via its WSDL, which lists its operations, the URL endpoints, and so on.

The Physician application, in a real-life situation, would be deployed on a separate WebLogic Server instance from the main MedRec application. The PhysicianSessionEJB, therefore, needs a way to communicate with the MedRec application over the Internet; using the operations of the MedRecWebServices Web Service is the ideal way to do this. The client JAR file generated by the clientgen Ant task contains the JAX-RPC stubs needed to invoke the Web Service operations—the amount of code you need to actually write in the EJB is very small.

The stand-alone Java client works almost the same as the EJB, except that the stand-alone client also needs the Web Services runtime client JAR file in its CLASSPATH; the EJB uses the runtime files contained in WebLogic Server.

Related Reading

- Programming WebLogic Web Services
- Programming WebLogic XML
- Programming WebLogic Enterprise Java Beans
- Java API for XML-Based RPC (JAX-RPC) 1.0 Specification
- Simple Object Access Protocol (SOAP) 1.1 Specification
- Web Services Description Language (WSDL) 1.1 Specification
- Java Swing