The latest packaged releases are available at http://www.extreme.indiana.edu/xgws/ and the latest source (if you want to be on the cutting edge) can now be obtained now from anonymous CVS at:
cvs -d :pserver:anonymous@cvs.extreme.indiana.edu:/l/extreme/cvspub login CVS password: cvsanon cvs -d :pserver:anonymous@cvs.extreme.indiana.edu:/l/extreme/cvspub co xsoap-java
By default XSOAP will give first parameter name the name of operation and next parameter will be 'p2', next 'p3' and so on. This is unfortunate consequence of Java introspection (java.lang.reflect) that does not allow to get parameter names. If the Java class was compiled with debug info it is possible to extract from debugging info names of parameters but it is not reliable solution (if debug info is not included you can not do much ..) and requires special 'super' introspection libraries (one more jar to include in XSOAP ...).
Instead in XSOAP version 1.2.11+ you can easily map parameter names to any name you like explicitly by calling XSOAP mapping API, for an example see HelloServiceMapping in samples/hello directory that demonstrates how to map parameters of sayHello methid from HelloService interface.
The file with XML schema type declarations should be compiled to generate Java Beans using such tool as Castor.
You can find example of this approach in Google API sample (src/java/samples/google) - look on included XML schema file (GoogleSearchResult.xsd) and Java Beans classes generated by Castor (GoogleSearchResult.java etc.).
From XSOAP version 1.2.12 it is now possible to use XmlNode to represent any XML content. Simply declare one of method parameters as XmlNode or as return type. XmlNode class is similar to DOM Node but it is much more lightweight (for description of XPP3 incremental document object and how it compares with other Java XML DOM APIs model please see an article in Javaworld).
For example it is used in in very simple OGSA sample (src/java/samples/ogsa) to process ServiceData elements. First in the interface GridService method FindServiceData is defined to take and return XmlNode:
public XmlNode FindServiceData(XmlNode xmlAsTree) throws RemoteException;
and this method when implemented in GridServiceImpl it uses XPP3 XmlNode API to access parts of XML tree and then a simple utility function that converts response XML string to XmlNode to return it (XmlNode could be also constructed directly and then returned).
To trace only SOAP message exchange use special XSOAP loggers:
soaprmi.trace.dispatch: to see all sever side activity
(receiving messages and sending responses)
soaprmi.trace.invoke: to trace RPC request and response messages
For example:
-Dlog=soaprmi.trace
-Dlog=soaprmi.trace.invoke -Dlog=soaprmi.trace.dispatch -Dlog=soaprmi.trace.invoke.out Moreover when you enable debug (-Ddebug) XSOAP logging output will include also all XSOAP message processing both client and server side.
to do this one need to start embedded HTTP server on this TCP port and use it for all exported remote objects (services). simple doing export will not work:
RemoteRef ref1 = UnicastRemoteObject.exportObject(obj1, 80);
RemoteRef ref2 = UnicastRemoteObject.exportObject(obj1, 80);
as second exportObject will try to start new HTTP server on the same TCP port so there will be network exception that this TCP port is already used:
could not start default dispatcher; nested exception is: java.net.BindException: Address in use: JVM_Bind at java.net.PlainSocketImpl.socketBind(Native Method) at java.net.PlainSocketImpl.bind(PlainSocketImpl.java:405) at java.net.ServerSocket.(ServerSocket.java:170) at java.net.ServerSocket. (ServerSocket.java:82) at soaprmi.soaprpc.PlainServerSocketFactory. (PlainServerSocketFactory.java:40) at soaprmi.soaprpc.PlainServerSocketFactory.newInstance(PlainServerSocketFactory.java:49) at soaprmi.soaprpc.HttpSocketSoapServerFactory.newSoapServer(HttpSocketSoapServerFactory.java:43) at soaprmi.soaprpc.SoapServices.addDefaultDispatcher(SoapServices.java:115) at soaprmi.server.Services.createPort(Services.java:116)
instead different approach must be take - this will work just fine when HTTP embedded server (more precisely Dispatcher) is shared:
import soaprmi.server.Services;
import soaprmi.server.UnicastRemoteObject;
import soaprmi.soaprpc.SoapServices;
Services services = SoapServices.newInstance(80);
services.setMapping(soaprmi.soap.Soap.getDefault().getMapping());
RemoteRef ref1 = UnicastRemoteObject.exportObject(obj1, services);
RemoteRef ref2 = UnicastRemoteObject.exportObject(obj2, services);
Then make sure that when usning object you pass not generic URL (http://host:port)
but full URL that contains object path, for example:
http://192.168.1.100:7890/GUID_1038105449175_1595867776_1
That URL can be obtained from XSOAP by using following code:
String remoteService1Url = SoapServices.getDefault().getStartpointLocation(ref1);
This question is hinting at bigger problem of associating addition information with the SOAP RPC call. This information is not global but rather thread specific (not shared between threads).
To create a generic solution that will work both on client and server side we have added soaprmi.server.ConnectionContext interface that represents information that will be used when XSOAP connection is created by client or received by server.
Send them to XSOAP mailing list.