|
by Samudra Gupta
Using SOAP with Java – part 3
Welcome back again to the
last part of this three series article on using SOAP with Java. In the previous
installments, we examined the basic anatomy of SOAP, developed a very simple
application and then converted the same application to a Java bean based SOAP
application. We also analysed in great detail in a short space how the
(De-)Serialization works in the SOAP context. Many of you might have been quite
pleased with the capabilities of Apache SOAP implementation but others might
have been waiting for a little more to watch. This month we will examine the
concept of writing our own Serializers and Deserializers.
Writing a Serializer
We have specified the basic requirement to pass a
user-defined data-type as a parameter to a SOAP service is that the data-type
must be a data-type handled by the Apache SOAP implementation that is to say the
data-types for which the Apache SOAP implementation already provides Serializers
and Deserializers or it must conform to a Java bean specification in order that
we may user the BeanSerializer class to Serialize and Deserialize them. But in the
real world, the applications might exchange data-types that fit into neither of
the above categories. For those data-types we can write our own (De-)Serializers.
For the sake of simplicity, we will try to write a (De-)Serializer for the
Person object that we have used in our previous Java bean based example.
According to the Apache SOAP implementation any Serializer must implement the
the org.apache.soap.util.xml.Serializer interface. Similarly, any Deserializer
must implement the org.apache.soap.util.xml.Deserializer interface. These interfaces
respectively declare two methods marshall() and unmarshall() to serialize and
deserialize the Java data-type in the context to and from XML document instance.
public class PersonSerializer extends Object implements Serializer, Deserializer
{
In order to write our own serialization and deserialization algorithm, we
need to override those methods.
public void marshall(String inScopeEncStyle,Class javaType,Object src,
Object context,Writer sink,NSStack nsStack,
XMLJavaMappingRegistry xjmr,SOAPContext ctx)
throws IllegalArgumentException,IOException
{
The parameters to the marshall method represent the following properties:
-
inScopeEncStyle : This represents the encodingStyleURI as specified
in the enclosing Call or Response object.
-
javaType : This is the run-time type of the object that is to be serialized.
-
src : This is a reference to the Java object to be serialized.
-
context : A String denoting the accessor name It must be non-null.
-
sink : The destination sink to which the SOAP XML instance will be written.
-
nsStack : A data structure that implements a stack of
namespace declarations that are currently in scope.
-
xjmr : This is the XMLJavaMappingRegistry object.
-
ctx : This is used to pass in things like javax.servlet.http.HttpServletRequest and
javax.servlet.http.HttpSession from the servlet context.
First of all, we need to create a new namespace scope in the nsStack
object:
//pushing the scope
nsStack.pushScope();
The NSStack class is used to keep a track of all the namespaces being used
within the application call and can be used to query a namespace with a given
uri. At this point of time, it is important to recollect how the Person object
graph will appear in an XML instance:
public class Person extends Object {
/** Holds value of property name. */
public String name;
/** Holds value of property age. */
public int age;
The above Person class will translate into the following XML instance
after serialization:
<serviceParam xmlns:ns2=”some uri” xsi:type=”ns2:Person”>
<age xsi:type=” xsd:int”>22</age>
<name xsi:type=xsd:string”>Paul</name>
</serviceParam>
Thus in order to write our serialization algorithm, we need to generate
the opening element structure header, then compute and serialize the value of
the object and then close the element. To generate the structure header for the
element, we do the following:
//generating the header structure
SoapEncUtils.generateStructureHeader(inScopeEncStyle, javaType, context,
sink, nsStack, xjmr);
sink.write(StringUtils.lineSeparator);
The second line in the above code snippet does nothing but add a
newline character to the whole generated header. Now we need to find out the
value of the different attributes present in the Java object and serialize them:
//obtaining the Person object out of the argument
Person person = (Person)src;
String name = person.getName();
int age = person.getAge();
if(name !=null)
{
xjmr.marshall(inScopeEncStyle, String.class, name, "name", sink, nsStack, ctx);
//fill the gap for the age parameter yourself……
sink.write(StringUtils.lineSeparator);
}
In the above code snippet, we determine the values of the attribute name
and age, notice the type of the each parameter and then call the marshall method
of the XMLJavaMappingRegistry class by passing the corresponding type of the
parameter. I have left the marshalling of the age parameter as an exercise to
you. When we pass the appropriate data-type for the parameter to be serialized,
the marshall method of the SOAPMappingRegistry will automatically call the
appropriate Serializer for the specified data-type. Finally, we need to
close the element by calling:
//closing the element
sink.write("</" + context + '>');
As you might have already guessed that if the Java object is a compound
type consisting of other complex types, then we need to apply this serialization
mechanism to every complex element recursively.
New on the Java Boutique:
New Review:
Time Management Made Easy with the Quartz Enterprise Job Scheduler
Why not just use the Java timer API? This open source scheduling
API boasts simplicity, ease-of-integration, a well-rounded feature
set, and it's free!
New Applet:
Reverse Complement
Reverse Complement is a simple applet that converts DNA or RNA
sequences into three useful formats.
Elsewhere on internet.com:
WebDeveloper Java
Lots of Java information on webdeveloper.com
WDVL Java
Thorough Java resource at the Web Developer's Virtual Library.
ScriptSearch Java
Hundreds of free Java code files to download.
jGuru: Your View of the Java Universe
Customizable portal with online training, FAQs, regular news updates, and tutorials.
|