Avitek Medical Records Development Tutorials

     Previous  Next    Open TOC in new window    View as PDF - New Window  Get Adobe Reader - New Window
Content starts here

 


Developing the MedRec Applications

 


Tutorial 12: Invoking a Web Service from a Client Application

This tutorial describes how to invoke the MedRecWebServices WebLogic Web Service (contained in the medrecEar application) that you created in Tutorial 11: Creating a Java EE Web Service by Programming a JWS File from the following types of client applications:

Stateless session EJBs and stand-alone Java clients use the client-side artifacts generated by the clientgen Ant task 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.

The clientgen WebLogic Web Services Ant task generates, from an existing WSDL file, the client artifacts that client applications use to invoke both WebLogic and non-WebLogic Web Services. These artifacts include:

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

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. If you have not already done so, start MedRecServer and Pointbase. See Step 4: Start the MedRec Administration Server. and Step 1: Start the PointBase database..
  2. Open a command window and set your environment:
  3. prompt> c:\bea\user_projects\domains\MedRecDomain\bin\setDomainEnv.cmd
  4. Move to the root physicianEar source directory and execute the ant command to compiled its components:
  5. prompt> cd c:\medrec_tutorial\src\physicianEar
    prompt> ant

    Although this tutorial shows how to build a Web Service in the physicianEar application, it is assumed that other components of physicianEar, such as the value objects, have already been compiled, which is why this step is required.

  6. Move to the root medrecEar source directory and execute the following ant commands to first build medrecEar (including its MedRecWebServices service that you are going to invoke in this tutorial) and then deploy the application:
  7. prompt> cd c:\medrec_tutorial\src\medrecEar
    prompt> ant build.split.dir
    prompt> ant build.ws
    prompt> ant appc.splitdir
    prompt> ant deploy.medrec.ear

 


Procedure

Each of the following steps shows the code excerpt needed to invoke a Web Service from a different type of client application.

Step 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, and then walks you through the EJB code in the PhysicianSessionEJB used to invoke the Web Service.

  1. Open a command window and set your environment:
  2. prompt> c:\bea\user_projects\domains\MedRecDomain\bin\setDomainEnv.cmd
  3. Change to the physicianEar subdirectory of the MedRec project directory:
  4. prompt> cd c:\medrec_tutorial\src\physicianEar
  5. Use a text editor to create a file called my_webserv_client.xml file:
  6. prompt> notepad my_webserv_client.xml
  7. Add the following lines to the my_webserv_client.xml file (substituting, if necessary, your actual MedRec project directory for c:\medrec_tutorial).
  8. 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">
      <taskdef name="clientgen"
    classname="weblogic.wsee.tools.anttasks.ClientGenTask" />
      <target name="build.ws.client">
        <clientgen
    wsdl="http://localhost:7101/ws_medrec/MedRecWebServices?WSDL"
    destDir="c:/medrec_tutorial/build/physicianEar/APP-INF/classes"
    packageName="com.bea.medrec.webservices.client"
    classpath="${java.class.path};c:/medrec_tutorial/build/physicianEar/APP-INF/lib/value.jar"/>
        <delete includeEmptyDirs="true" failonerror="false" quiet="false">
    <fileset dir="c:/medrec_tutorial/build/physicianEar/APP-INF/classes/com/bea/medrec/value"/>
    </delete>
        <javac
    srcdir="c:/medrec_tutorial/build/physicianEar/APP-INF/classes/com"
    includes="**/*.java"
    classpath="${java.class.path};c:/medrec_tutorial/build/physicianEar/APP-INF/lib/value.jar;c:/medrec_tutorial/build/physicianEar/APP-INF/classes"/>
      </target>
    </project>

    The Ant build file first shows how you use the taskdef task to specify the full classname of the clientgen Ant task.

    The Ant build file then calls the clientgen Web Services Ant task which generates the client-side artifacts needed to invoke a Web Service. The wsdl attribute specifies that the clientgen Ant task use the WSDL of the WebLogic Web Service you deployed in Tutorial 11: Creating a Java EE Web Service by Programming a JWS File when generating the artifacts. The destdir attribute specifies that clientgen generate its artifacts into the APP-INF/classes directory of the physicianEar build directory. The APP-INF directory is part of the WebLogic split development directory environment and is used to ensure that the generated classes are available to other modules, such as the PhysicianSessionEJB, in the deployed application. The packageName attribute is used to specify the package into which Java code is generated. Finally, the classpath attribute updates the CLASSPATH with the value.jar JAR file that contains the compiled value-classes of the user-defined data types, such as Patient and Record.

    In this release of WebLogic Server, however, there is no way to tell the clientgen Ant task not to generate Java representations of the user-defined data types in the WSDL file, or in other words, the same value-classes that already exist in the value.jar file. The classes generated by clientgen do not include additional methods added to the custom value classes that are required by the MedRec application. For this reason, you must include the delete task in the build.xml to delete the clientgen-generated classes so that they are not inadvertently used by the MedRec application.

    Because clientgen generates uncompiled Java classes, the build file then calls the javac task to compile all generated code.

    Note: In the preceding Ant build file, it is assumed that the MedRecWebServices WebLogic Web Service is deployed to WebLogic Server and its WSDL is accessible. This is the typical way you always run the clientgen Ant task. However, if you have not yet deployed the Web Service, you can point the wsdl attribute to a static WSDL file, in particular the one that was generated when you compiled the medrecEar application that contains the MedRecWebServices service. To use the static WSDL file, update the wsdl attribute of the clientgen task in my_webserv_client.xml as shown:
        <clientgen
    wsdl="c:/medrec_tutorial/build/medrecEar/MedRecWebServices/WEB-INF/MedRecWebServices.wsdl"
    ...
  9. Execute the clientgen Ant task by running the my_webserv_client.xml script:
  10. prompt> ant -f my_webserv_client.xml

    The clientgen Ant task shows output similar to the following:

    Buildfile: my_webserv_client.xml
    Trying to override old definition of task clientgen
    build.ws.client:
    [clientgen]
    [clientgen] *********** jax-rpc clientgen attribute settings ***************
    [clientgen]
    [clientgen] wsdlURI: http://localhost:7101/ws_medrec/MedRecWebServices?WSDL
    [clientgen] serviceName : null
    [clientgen] packageName : com.bea.medrec.webservices.client
    [clientgen] destDir : C:\medrec_tutorial\build\physicianEar\APP-INF\classes
    [clientgen] handlerChainFile : null
    [clientgen] generatePolicyMethods : false
    [clientgen] autoDetectWrapped : true
    [clientgen] jaxRPCWrappedArrayStyle : true
    [clientgen] generateAsyncMethods : true
    [clientgen]
    [clientgen] *********** jax-rpc clientgen attribute settings end ***************
    [clientgen] Package name is com.bea.medrec.webservices.client
    [clientgen] DestDir is C:\medrec_tutorial\build\physicianEar\APP-INF\classes
    [clientgen] class name is MedRecWebServicesPortType_Stub
    [clientgen] service class name is MedRecWebServices
    [clientgen] Porttype name is MedRecWebServicesPortType
    [clientgen] service impl name is MedRecWebServices_Impl
    [delete] Deleting 8 files from C:\medrec_tutorial\build\physicianEar\APP-INF\classes\com\bea\medrec\value
    [delete] Deleted 1 directory from C:\medrec_tutorial\build\physicianEar\APP-INF\classes\com\bea\medrec\value
    [javac] Compiling 5 source files
    [javac] Note: C:\medrec_tutorial\build\physicianEar\APP-INF\classes\com\bea\medrec\webservices\client\MedRecWebServicesPortType_Stub.java uses unchecked orunsafe operations.
    [javac] Note: Recompile with -Xlint:unchecked for details.
    BUILD SUCCESSFUL
    Total time: 10 seconds
  11. Update the PhysicianSessionEJB to invoke the Web Service.
  12. Note: This part of the tutorial simply walks you through the EJB code you would write; the PhysicianSessionEJB.ejb code in the medrecEar application already contains the code needed to invoke the MedRecWebServices Web Service.
    1. Change to the directory that contains the PhysicianSessionEJB Java code:
    2. prompt> cd c:\medrec_tutorial\src\physicianEar\physSessionEjbs\com\bea\medrec\controller
    3. Open the PhysicianSessionEJB.ejb file in an IDE or text editor:
    4. prompt> notepad PhysicianSessionEJB.ejb
    5. Search for the private method getMedRecWebServicesPort(). This method contains the standard Java code that creates a JAX-RPC port of the MedRecWebServices Web Service, shown in bold:
    6. wsUrl = (String) initCtx.lookup("java:comp/env/webservice/url");
      wsUsername = (String) initCtx.lookup("java:comp/env/webservice/username");
      wsPassword = (String) initCtx.lookup("java:comp/env/webservice/password");
      logger.debug("MedRec Web Service URL: " + wsUrl);
      MedRecWebServices service = new MedRecWebServices_Impl(wsUrl+"?WSDL");
      port = service.getMedRecWebServicesPort(wsUsername, wsPassword);

      The URL of the WSDL of the deployed MedRecWebServices, as well as the user and password of the user that will invoke the Web Service, is defined using the @EnvEntries EJBGen annotation at the beginning of the PhysicianSessionEJB.ejb file. The actual URL is:

      http://host:7101/ws_medrec/MedRecWebServices?WSDL

      where host is the name of the computer hosting MedRec.

    7. The public methods of PhysicianSessionEJB use the JAX-RPC port you created in the preceding step to invoke Web Service operations.
    8. For example, search for the public method getRecord. The implementation of the method contains the following Java code that invokes the getRecord operation of the MedRecWebServices Web Service by using the port instance created in the preceding step:

       // Get record from MedRec.
      recordVO = port.getRecord(pRecordId.intValue());
  13. Compile, deploy, and run PhysicianSessionEJB as usual.
  14. For information about compiling, see Tutorial 7: Compiling Split Development Directory Applications with Ant Tasks.

Step 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, and then walks you through the actual Java client code you need to write. It is assumed that you know how to write, compile, and run a Java Swing client application.

  1. Open a command window and set your environment:
  2. prompt> c:\bea\user_projects\domains\MedRecDomain\bin\setDomainEnv.cmd
  3. Change to the clients subdirectory of the MedRec project directory:
  4. prompt> cd c:\medrec_tutorial\src\clients
  5. Use a text editor to create a file called my_webserv_client.xml file:
  6. prompt> notepad my_webserv_client.xml
  7. Add the following lines to the my_webserv_client.xml file (substituting, if necessary, your actual MedRec project directory for c:/medrec_tutorial).
  8. 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" >
     <taskdef name="clientgen"
    classname="weblogic.wsee.tools.anttasks.ClientGenTask" />
      <target name="build.ws.client">
        <clientgen
    wsdl="http://localhost:7101/ws_medrec/MedRecWebServices?WSDL"
    destDir="c:/medrec_tutorial/build/swing_client/clientgen"
    packageName="com.bea.medrec.webservices"/>
        <javac
    srcdir="c:/medrec_tutorial/build/swing_client/clientgen"
    destdir="c:/medrec_tutorial/build/swing_client/wsclient"
    includes="**/*.java"/>
        <javac
    srcdir="com"
    destdir="c:/medrec_tutorial/build/swing_client/wsclient"
    includes="**/*.java"
    classpath="${java.class.path};c:/medrec_tutorial/build/swing_client/wsclient" />
      </target>
    </project>

    The Ant build file first uses the taskdef task to specify the full classname of the clientgen Ant task.

    The Ant build file then calls the clientgen Web Services Ant task, which generates the client-side artifacts needed to invoke a Web Service. The wsdl attribute specifies that the clientgen Ant task use the WSDL of the WebLogic Web Service you deployed in Tutorial 11: Creating a Java EE Web Service by Programming a JWS File when generating the artifacts. The destdir attribute specifies that clientgen generate its artifacts into the c:/medrec_tutorial/build/swing_client/clientgen directory. The packageName attribute specifies the package into which Java code is generated.

    Because clientgen generates uncompiled Java classes, the build file then calls the javac task to compile all generated code. The second javac task compiles the Swing client itself (whose source code is located in c:\medrec_tutorial\src\clients\com) into the same directory into which the clientgen-generated Java code was compiled.

    Note: In the preceding Ant build file, it is assumed that the MedRecWebServices WebLogic Web Service is deployed to WebLogic Server and its WSDL is accessible. This is the typical way you run the clientgen Ant task. However, if you have not yet deployed the Web Service, you can point the wsdl attribute to a static WSDL file, in particular the one that was generated when you compiled the medrecEar application that contains the MedRecWebServices service. To use the static WSDL file, update the wsdl attribute of the clientgen task in my_webserv_client.xml as shown:
        <clientgen
    wsdl="c:/medrec_tutorial/build/medrecEar/MedRecWebServices/WEB-INF/MedRecWebServices.wsdl"
    ...
  9. Execute the clientgen Ant task by running the my_webserv_client.xml script:
  10. prompt> ant -f my_webserv_client.xml

    The clientgen Ant task shows the following output:

    Buildfile: my_webserv_client.xml
    Trying to override old definition of task clientgen
    build.ws.client:
    [clientgen]
    [clientgen] *********** jax-rpc clientgen attribute settings ***************
    [clientgen]
    [clientgen] wsdlURI: http://localhost:7101/ws_medrec/MedRecWebServices?WSDL
    [clientgen] serviceName : null
    [clientgen] packageName : com.bea.medrec.webservices
    [clientgen] destDir : C:\medrec_tutorial\build\swing_client\clientgen
    [clientgen] handlerChainFile : null
    [clientgen] generatePolicyMethods : false
    [clientgen] autoDetectWrapped : true
    [clientgen] jaxRPCWrappedArrayStyle : true
    [clientgen] generateAsyncMethods : true
    [clientgen]
    [clientgen] *********** jax-rpc clientgen attribute settings end ***************
    [clientgen] Package name is com.bea.medrec.webservices
    [clientgen] DestDir is C:\medrec_tutorial\build\swing_client\clientgen
    [clientgen] class name is MedRecWebServicesPortType_Stub
    [clientgen] service class name is MedRecWebServices
    [clientgen] Porttype name is MedRecWebServicesPortType
    [clientgen] service impl name is MedRecWebServices_Impl
    [javac] Compiling 13 source files to C:\medrec_tutorial\build\swing_client\wsclient
    [javac] Note: C:\medrec_tutorial\build\swing_client\clientgen\com\bea\medrec\webservices\MedRecWebServicesPortType_Stub.java uses unchecked or unsafe operations.
    [javac] Note: Recompile with -Xlint:unchecked for details.
    [javac] Compiling 4 source files to C:\medrec_tutorial\build\swing_client\wsclient
    BUILD SUCCESSFUL
    Total time: 14 seconds
  11. Update the stand-alone Java Swing client application to invoke the Web Service.
  12. 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:
    2. prompt> cd c:\medrec_tutorial\src\clients\com\bea\medrec\webservices\swing
    3. Open the EditProfileFrame.java file in your favorite IDE or text editor:
    4. prompt> notepad EditProfileFrame.java
    5. 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:
    6. MedRecWebServices ws =
      new MedRecWebServices_Impl(this.WSDLTextField.getText());
      MedRecWebServicesPortType port  = ws.getMedRecWebServicesPort();
      Patient Patient =
      (Patient)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.

    7. Search for the method saveButton_actionPerformed(ActionEvent e), which saves updated patient information to the MedRec application by invoking the updatePatient Web Service operation on the JAX-RPC stub port, created in the preceding step:
    8. port.updatePatient(patient);
  13. Change to the main source directory for the client applications:
  14. prompt> cd c:\medrec_tutorial\src\clients
  15. Run the application using the run target in the existing build.xml file:
  16. prompt> ant -f build.xml run

    In the application, enter a Social Security number of 123456789 in the Enter Patient SSN field and click Submit. If the MedRec application is deployed and running correctly, you will see information returned about the patient Fred Winner.

Step 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 (Version 1.1) on your computer before you can create and run the C# client. See Microsoft .NET Framework Development Center.

The sample C# client that invokes the MedRecWebServices WebLogic Web Service is in the following directory:

prompt> cd c:\medrec_tutorial\src\clients\CSharpClient

To run the client, either rebuild it using the .NET IDE, or execute the following already-built application:

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

In the application, enter a Social Security number of 123456789 in the Enter Patient SSN field and click Submit. If the MedRec application is deployed and running correctly, you will see information returned about the patient Fred Winner.

Caution: The already-built client is hard-coded to invoke the MedRecWebService deployed at http://localhost:7011, so be sure to update the wsdl location field of the client with the host and port number of your own MedRecServer (http://localhost:7101 by default).

 


Best Practices

 


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: Creating a Java EE Web Service by Programming a JWS File, 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-side artifacts 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 essentially the same way as the EJB as far as using the artifacts generated by clientgen.

 


Related Reading


  Back to Top       Previous  Next