How to deseralize a hashtable?
"Chen, Donald" <[email protected]>
| Newsgroups | gmane.text.xml.soap.user |
|---|---|
| Message-ID | <[email protected]> |
Hi, All.
I have a WS in Perl via SOAP::Lite. Via this WS, a client can call a
method getAllInfo() which returns a
Hashtable. I wrote a WS client in perl with success, but writing a WS
client in Java via the Apache-Soap-2.3.1 is never successful.
Specifically, the error I got is like this:
Exception in thread "main" java.lang.IllegalArgumentException: No
Deserializer found to deserialize a
'http://xml.apache.org/xml-soap:SOAPStruct' using encoding style
'http://schemas.xmlsoap.org/soap/encoding/'.
at
org.apache.soap.util.xml.XMLJavaMappingRegistry.queryDeserializer(XMLJav
aMappingRegistry.java:206)
at
org.apache.soap.util.xml.XMLJavaMappingRegistry.unmarshall(XMLJavaMappin
gRegistry.java:302)
at
org.apache.soap.encoding.soapenc.ParameterSerializer.unmarshall(Paramete
rSerializer.java:206)
at
org.apache.soap.util.xml.XMLJavaMappingRegistry.unmarshall(XMLJavaMappin
gRegistry.java:314)
at
org.apache.soap.rpc.RPCMessage.unmarshall(RPCMessage.java:417)
at
org.apache.soap.rpc.RPCMessage.extractFromEnvelope(RPCMessage.java:197)
at
org.apache.soap.rpc.Response.extractFromEnvelope(Response.java:142)
at GetChemDef.main(GetChemDef.java:167)
Here is the payload I got from the server:
<?xml version="1.0" encoding="UTF-8"?><SOAP-ENV:Envelope
xmlns:namesp2="http://xml.apache.org/xml-soap"
SOAP-ENV:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:SOAP-ENC="http://schemas.xmlsoap.org/soap/encoding/"
xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"><SOAP-ENV:Body><namesp17:ge
tAllInfoResponse
xmlns:namesp17="http://johnny5:8002/ChemDefServices"><s-gensym68
xsi:type="namesp2:SOAPStruct"><delimilator
xsi:type="xsd:string">|</delimilator><chemistry
xsi:type="xsd:string">caffeine</chemistry><a
xsi:type="xsd:string">aPiece</a><smiles
xsi:type="xsd:string">c1ccccc1</smiles><b
xsi:type="xsd:string">bPiece</b><syntaxOk
xsi:type="xsd:int">1</syntaxOk></s-gensym68></namesp17:getAllInfoRespons
e></SOAP-ENV:Body></SOAP-ENV:Envelope>
This payload refects a hashtable:
%h = ( chemistry => 'caffeine',
a => 'aPiece',
b => 'bPiece',
smiles => 'c1ccccc1'
);
Here are the major code lines (as you can see, I was trying to use the
HashtableSerializer ):
// build the call.
Call call = new Call();
call.setSOAPTransport(st);
call.setTargetObjectURI("http://localhost:8002/ChemDefServices");
call.setMethodName("getAllInfo");
SOAPMappingRegistry smrr = new SOAPMappingRegistry ();
HashtableSerializer hsd = new HashtableSerializer ();
smrr.mapTypes(Constants.NS_URI_SOAP_ENC, new QName("",
"ChemDefServices"), Hashtable.class, null, hsd);
// create the transport and set parameters
call.setEncodingStyleURI(Constants.NS_URI_SOAP_ENC);
call.setSOAPMappingRegistry(smrr);
Vector params = new Vector();
params.addElement(new Parameter("definition", String.class,
"definition", null));
params.addElement(new Parameter("chemDefString", String.class,
chemDefString, null));
call.setParams(params);
// invoke it
System.err.println("Invoking chemDef service at: ");
System.err.println("\t" + serviceURL);
Response resp;
try {
SOAPMappingRegistry smr = call.getSOAPMappingRegistry();
SOAPContext reqCtx = call.getSOAPContext();
DocumentBuilder xdb = XMLParserUtils.getXMLDocBuilder();
Envelope callEnv = call.buildEnvelope();
StringWriter payloadSW = new StringWriter();
callEnv.marshall(payloadSW, smr, reqCtx);
reqCtx.setRootPart(payloadSW.toString(),
Constants.HEADERVAL_CONTENT_TYPE);
st.send(url, "", null, null, smr, reqCtx);
SOAPContext respCtx = st.getResponseSOAPContext();
String payloadStr = Call.getEnvelopeString(st);
Document respDoc = xdb.parse(new InputSource(new
StringReader(payloadStr)));
Element payload = null;
if (respDoc != null) {
payload = respDoc.getDocumentElement();
} else {
throw new SOAPException (Constants.FAULT_CODE_CLIENT,
"Parsing error, response was:\n" + payloadStr);
}
System.out.println("payloadStr = \n" + payloadStr);
Envelope respEnv = Envelope.unmarshall(payload, respCtx);
System.out.println("respEnv = \n" + respEnv.toString());
System.out.println("respCtx = \n" + respCtx.toString());
resp = Response.extractFromEnvelope(respEnv, smr, respCtx);
// I got error right here
Did I miss something to make it work? Do I need to write my own
deseralizer for the hashtable? If yes, how to incorporate the
deseralizer to the main funciton?
Thanks in advance,
Donald