Thursday, December 11, 2003


Web Service Tip: JSPs Calling Web Services

How do I call a Web service from a JSP?  Seems like a simple question but it turns out there are many ways - some quick and dirty and others more correct.  Let's not debate correctness (do you really want to do this?!) and first solve the problem.

Imagine, if you will, I have generated a stub from the wsdl of  the greeting Web service built a few days ago (again, I refer you to the OTN tutorial step 16 for more details on generating the stub).  

If I add a main method to that stub, I can easily test that stub against my Web service:

  public static void main(String[] args)  {
    try {
      GreetingServiceStub stub = new GreetingServiceStub();
      System.out.println(stub.sayHello("Mike"));
    }
    catch(Exception ex) {
      ex.printStackTrace();
    }
  }

That bit of code, will become the foundation of how to do my first cut of calling of a Web service from a JSP. The JSP page I want to hook it into looks like this:

First I would like to make a direct call from my JSP.  All I have to do is add a scriplet based on that above code: 

<%@ page contentType="text/html;charset=windows-1252" import="com.rpc.GreetingServiceStub" %>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=windows-1252">
<title>
Web Service JSP Client - Scriptlet
</title>
</head>
<body>
<%
String parm1 = request.getParameter("parm1");
String result = "";
if (parm1 == null)
   parm1 = " ";
%>
<br>
<form action="Greeting.jsp" method="get">
  <table border="0">
    <tr>
      <td>
        Greeting:</b>
      </td>
      <td>
        <input type="text" name="parm1" size="14" value="<%=parm1 %>">
      </td>
      <td>
        <input type="Submit" value="Submit"/>
      </td>
      </tr>
  </table>
</form>
<p>
<br>
<%
try {
GreetingServiceStub stub = new GreetingServiceStub();
result = stub.sayHello(parm1);
}
catch (Exception e) {
result = "Web service unreachable tonight :-(";
}
%>
The response returned is:
<%=result %>
</body>
</html>

Note the import at the top of com.rpc.GreetingServiceStub which is the stub itself.  Not particularly elegant, but it gets the job done.

Abstracting it a little further, I could investigate Oracle's Web service tag library which takes away a bit of the code and makes it a little more declarative.  The extra work required here is of course reading the WSDL to get the binding, portType and the like.  See below for the same example using the tag library:

<%@ taglib uri="http://xmlns.oracle.com/j2ee/jsp/tld/ojsp/wstaglib.tld" prefix="wstag"%>
<%@ page contentType="text/html;charset=windows-1252"%>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=windows-1252">
<title>
Web Service JSP Client - Tag Library
</title>
</head>
<body>
<%
String parm1 = request.getParameter("parm1");
if (parm1 == null)
   parm1 = " ";
%>
<br>
<form action="GreetingTagLib.jsp" method="get">
  <table border="0">
    <tr>
      <td>
        Greeting:</b>
      </td>
      <td>
        <input type="text" name="parm1" size="14" value="<%=parm1 %>">
      </td>
      <td>
        <input type="Submit" value="Submit"/>
      </td>
      </tr>
  </table>
</form>
<p>


<wstag:webservice id="greeting"
  wsdlUrl="
http://127.0.0.1:8888/ws/GreetingService?WSDL"
  scope="page"
  binding="GreetingBinding"
  soapLocation="
http://127.0.0.1:8888/ws/GreetingService"/>
<wstag:invoke id="resp" webservice="greeting" operation="sayHello">
 <wstag:part name="p" value="<%=parm1 %>" />
</wstag:invoke>

<br>
The response returned is:
<%=pageContext.findAttribute("resp") %>

</body>
</html>

If you look again at the WSDL, you will see all the settings that were passed to the tags - e.g. GreetingBinding from the binding section and operation name from the portType section.  If you plan on trying this out yourself, you are probably wondering where this Web services tag library jar and tld is located.  If you look in your OracleAS 9.0.4 distribution, you will find the ojsputil.jar located in the <Oracle_Home>j2eehomejsplibtaglib - inside is the TLD.

Most likely in a larger application, for example using a more typical MVC framework like Struts, the call to from stub would be more likely be in an Apache Struts action or delegated to from a Struts action, rather than in the JSP page itself.  However, for the folks doing quick and dirties out there, these two routes can be a quick way to hook your Web service to a JSP.

As a by the by, if you are an Oracle Portal user you may want to investigate the OmniPortlet, which makes this whole exercise a declarative effort rather than a programmatic one.



comment []
6:25:59 AM