You are viewing a plain text version of this content. The canonical link for it is here.
Posted to java-dev@axis.apache.org by bu...@apache.org on 2003/03/12 15:33:35 UTC

DO NOT REPLY [Bug 17916] New: - Service.createCall() loses operation namespace URI

DO NOT REPLY TO THIS EMAIL, BUT PLEASE POST YOUR BUG 
RELATED COMMENTS THROUGH THE WEB INTERFACE AVAILABLE AT
<http://nagoya.apache.org/bugzilla/show_bug.cgi?id=17916>.
ANY REPLY MADE TO THIS MESSAGE WILL NOT BE COLLECTED AND 
INSERTED IN THE BUG DATABASE.

http://nagoya.apache.org/bugzilla/show_bug.cgi?id=17916

Service.createCall() loses operation namespace URI

           Summary: Service.createCall() loses operation namespace URI
           Product: Axis
           Version: 1.1RC1
          Platform: PC
        OS/Version: Windows NT/2K
            Status: NEW
          Severity: Normal
          Priority: Other
         Component: Basic Architecture
        AssignedTo: axis-dev@ws.apache.org
        ReportedBy: gary.gordon@softwareagusa.com


If you try to invoke an operation for an RPC-style service such that the 
operation name is required to be fully qualified (i.e. a QName), the service 
code internally drops the namespace URI when the Call is created from the 
Service.  In the generated SOAP message, the operation wrapper XML element 
lacks the namespace prefix and declaration (use TCP Monitor tool).  This proves 
to be a problem in interoperability tests with Web Services implemented with 
IONA's XMLBus, where the Web Service fails unless the operation name is fully 
qualified.

The problem is easily found in the Service source code in Axis:
public javax.xml.rpc.Call createCall(QName portName, QName operationName)
throws ServiceException {
  Call call = (org.apache.axis.client.Call)createCall();
  call.setOperation( portName, operationName.getLocalPart() );
  return( call );
}

The workaround is that when you do Call.invoke() you must use the version of 
invoke() that takes both the operation name and the array of parameters.  Using 
the signature that just takes the parameters fails.  Here is a test program 
invoking the XMLBus service that demonstrates this behavior (it uses 
attachments, but it is the best example I found):

==================================================================

import org.apache.axis.AxisFault;
import javax.xml.rpc.Call;
import javax.xml.rpc.Service;
import javax.xml.rpc.ServiceFactory;

import java.io.ByteArrayInputStream;
import java.net.URL;
import javax.xml.namespace.QName;
import javax.xml.transform.stream.StreamSource;

public class BugTest {
  public static void main(String[] args) throws Exception {
    String wsdlUrl =
"http://www.xmlbus.com:9010/xmlbus/container/AttachmentApp/AttachmentAppService/
AttachmentAppPort/";
    String targetNS = "urn:AttachmentService";
    QName portQN = new QName(targetNS, "AttachmentAppPort");
    QName serviceQN = new QName(targetNS, "AttachmentAppService");
    QName operation = new QName(targetNS, "doXML");
    Service service = ServiceFactory.newInstance().createService(
      new URL(wsdlUrl), serviceQN);
    Call call = (Call) service.createCall(portQN, operation);
    byte[] doc = "<doc/>".getBytes();
    Object res = null;
    boolean succeeded = true;
    try {
      res = call.invoke(
        new Object[] { new StreamSource(new ByteArrayInputStream(doc)) }
      );
    } catch (AxisFault af) {
      succeeded = false;
    }
    System.out.println("invoke WITHOUT operation param " +
      (succeeded ? "succeeded" : "failed"));
		
    succeeded = true;
    try {
      res = call.invoke(
        operation,
        new Object[] { new StreamSource(new ByteArrayInputStream(doc)) }
      );
    } catch (AxisFault af) {
      succeeded = false;
    }
    System.out.println("invoke WITH operation param " +
     (succeeded ? "succeeded" : "failed"));
  }
}
==================================================================


While the various SOAP/WSDL/JAX-RPC specs are a little vague about the 
requirements for the format of the operation wrapper, I did find the following 
in the WSDL spec which indicates the namespace of the wrapper element should be 
the namespace found in the soap:body element of the WSDL.

==================================================================
section 3.5 soap:body

If the operation style is rpc each part is a parameter or a return value and 
appears inside a wrapper element within the body (following Section 7.1 of the 
SOAP specification). The wrapper element is named identically to the operation 
name and its namespace is the value of the namespace attribute.
==================================================================

Thus, whether or not we think XMLBus works the way it should, the fact remains 
that if I request Axis to use a fully qualified operation name, it should honor 
that request in the generated SOAP message, and the WSDL spec seems to back 
this up.

Gary