You are viewing a plain text version of this content. The canonical link for it is here.
Posted to soap-user@xml.apache.org by Erik van Zijst <er...@marketxs.com> on 2001/02/27 13:46:06 UTC

Serializing inherited classes (2)

Hi,

I'm running this question again because I still haven't found a solution, but 
I did run into the same question from others.
Obviously there's more to it than meets the eye:


I'm building a SOAP interface for the financial (web) services of our 
company. Currently we offer just RMI.

Ofcourse I want the SOAP interface to resemble the RMI interface as close as 
possible. As you'll understand we heavily rely on inherited classes that 
travel over the wire.
In RMI this is all straightforward, but SOAP seems to be another story.

I'll be using Apache-SOAP on the serverside. Since SOAP will be implemented 
on top of the existing RMI interface, I'll be writing my own serializers for 
our current return types.

My question is how to implement these serializers if they need to serialize 
subclasses.

Consider class A:

public class A
{
	private String param1;

	public A() {}
	public void setParam1(String param1) {
		this.param1 = param1;
	}
	public String getParam1() {
		return this.param1;
	}
}

and class B:

public class B extends A
{
	private String param2;

	public B() {}
	public void setParam2(String param2) {
		this.param2 = param2;
	}
	public String getParam2() {
		return this.param2;
	}
}

To serialize these, I figure I'd write ASerializer.java that will pretty much 
resemble the simpler serializers in src/org/apache/soap/encoding/soapenc and 
I'd write BSerializer that extends ASerializer and marshalls the variables in 
class B and then calls something like super.marshall().

Is that a correct solution? And what will the resulting xml envelope look 
like? What is the correct xml syntax of a serialized subclass anyway? Does 
anyone know of examples of serializing inherited classes?

P.S. the reason that I won't be using the BeanSerializer for this example is 
that my real classes need special treatment and contain logic.

FYI, I have no clue what language/toolkit my clients will be using.

Erik van Zijst
-- 
Trap full -- please empty.


Re: Serializing inherited classes (2)

Posted by Erik van Zijst <er...@marketxs.com>.
> In Java object serialization the JVM is the one doing the serialization.
> In a SOAP serializer, you have to explicitly write a serializer for
> subclasses too because the serializer can only serialize stuff it knows
> about and it doesn't know about the info in the subclass.

I was thinking of an externalizable-like approach. With externalizable, you 
implement what and how you write data to the wire in your class. I was 
thinking of a similar approach for the serializers.

> If you used your approach, here's what you'd get:
>
> Say A looked like this (using soap-encoding):
>     <A-xml>
>         <param1>value-of-param1</param1>
>     </A-xml>
> then B's serialization would look like:
>     <B-xml>
>         <A-xml>
>             <param1>value-of-param1</param1>
>         </A-xml>
>         <param2>value-of-param2</param2>
>     </B-xml>
>
> Is this "right"? If you interpret B-xml using the soap-enc rules then
> B-xml is a struct with two fields; a complex one (called A-xml) and
> a simple one (called param2). So you effectively lose the subtype
> relationship.

Not necessarily.
I could implement a public marshall() method in the serializers, as well as a 
private _marshall() method.
The public one pushes the namespace to the nsStack ( nsStack.pushScope() in 
Apache's serializers, so the <B-xml> tag is opened ) and then calls the 
private _marshall() method to write the actual members.

In action:
- BSerializer.marshall() gets called with an instance of B.
- It calls nsStack.pushScope(); to write <B-xml> to the envelope.
- Now it calls its private _marshall() method.
- The private _marshall() writes B's member to the envelope, yielding:

<B-xml>
    <param2>value-of-param2</param2>

- The private _marshall() calls super._marshall(), passing B (casted to A)
- The private _marshall() of the superclass (A) serializes the member of A:

<B-xml>
    <param2>value-of-param2</param2>
    <param1>value-of-param1</param1>

- super._marshall() returns.
- _marshall() returns.
- marshall() calls nsStack.popScope(); yieling:

<B-xml>
    <param2>value-of-param2</param2>
    <param1>value-of-param1</param1>
</B-xml>

With this approach my classes get serialized the way BeanSerializer works. 
The subtype relation is not encoded, but no data is lost.

The unmarshalling of the resulted xml would make Apache-SOAP call 
BSerializer.unmarshall(B).
In reverse order, BSerializer.unmarshall() calls BSerializer._unmarshall() to 
retrieve B's member and then call ASerializer._marshall() for the member of 
the superclass.

With this approach, the order of the members becomes very important however. 
Does that violate any specifications?

> If you really want to maintain the subtype relationship across the
> wire then you need to use a different encoding style.

I really want to stick to soap encoding and standards in general. Let's not 
forget what the 'S' in SOAP stands for :)

What do you think of my proposed solution? I wouldn't want to exclude the 
possibility of me overlooking some very fundamental things.

It's absolutely imperative I get this serializing properly done, or I might 
find myself writing yet another interface for yet another protocol.

Erik
-- 
And you can't get any Watney's Red Barrel,
because the bars close every time you're thirsty...

Re: Serializing inherited classes (2)

Posted by Erik van Zijst <er...@marketxs.com>.
> In Java object serialization the JVM is the one doing the serialization.
> In a SOAP serializer, you have to explicitly write a serializer for
> subclasses too because the serializer can only serialize stuff it knows
> about and it doesn't know about the info in the subclass.

I was thinking of an externalizable-like approach. With externalizable, you 
implement what and how you write data to the wire in your class. I was 
thinking of a similar approach for the serializers.

> If you used your approach, here's what you'd get:
>
> Say A looked like this (using soap-encoding):
>     <A-xml>
>         <param1>value-of-param1</param1>
>     </A-xml>
> then B's serialization would look like:
>     <B-xml>
>         <A-xml>
>             <param1>value-of-param1</param1>
>         </A-xml>
>         <param2>value-of-param2</param2>
>     </B-xml>
>
> Is this "right"? If you interpret B-xml using the soap-enc rules then
> B-xml is a struct with two fields; a complex one (called A-xml) and
> a simple one (called param2). So you effectively lose the subtype
> relationship.

Not necessarily.
I could implement a public marshall() method in the serializers, as well as a 
private _marshall() method.
The public one pushes the namespace to the nsStack ( nsStack.pushScope() in 
Apache's serializers, so the <B-xml> tag is opened ) and then calls the 
private _marshall() method to write the actual members.

In action:
- BSerializer.marshall() gets called with an instance of B.
- It calls nsStack.pushScope(); to write <B-xml> to the envelope.
- Now it calls its private _marshall() method.
- The private _marshall() writes B's member to the envelope, yielding:

<B-xml>
    <param2>value-of-param2</param2>

- The private _marshall() calls super._marshall(), passing B (casted to A)
- The private _marshall() of the superclass (A) serializes the member of A:

<B-xml>
    <param2>value-of-param2</param2>
    <param1>value-of-param1</param1>

- super._marshall() returns.
- _marshall() returns.
- marshall() calls nsStack.popScope(); yieling:

<B-xml>
    <param2>value-of-param2</param2>
    <param1>value-of-param1</param1>
</B-xml>

With this approach my classes get serialized the way BeanSerializer works. 
The subtype relation is not encoded, but no data is lost.

The unmarshalling of the resulted xml would make Apache-SOAP call 
BSerializer.unmarshall(B).
In reverse order, BSerializer.unmarshall() calls BSerializer._unmarshall() to 
retrieve B's member and then call ASerializer._marshall() for the member of 
the superclass.

With this approach, the order of the members becomes very important however. 
Does that violate any specifications?

> If you really want to maintain the subtype relationship across the
> wire then you need to use a different encoding style.

I really want to stick to soap encoding and standards in general. Let's not 
forget what the 'S' in SOAP stands for :)

What do you think of my proposed solution? I wouldn't want to exclude the 
possibility of me overlooking some very fundamental things.

It's absolutely imperative I get this serializing properly done, or I might 
find myself writing yet another interface for yet another protocol.

Erik
-- 
And you can't get any Watney's Red Barrel,
because the bars close every time you're thirsty...

Java Resultsets as SOAP parameters

Posted by Atilio Rosso - Up 2 U - Internet Solutions <ar...@up2u.com.ar>.
Is it possible to use a Java Resultset as a SOAP input and/or output
parameter?

Thanks, Atilio


Java Resultsets as SOAP parameters

Posted by Atilio Rosso - Up 2 U - Internet Solutions <ar...@up2u.com.ar>.
Is it possible to use a Java Resultset as a SOAP input and/or output
parameter?

Thanks, Atilio


Re: Serializing inherited classes (2)

Posted by Sanjiva Weerawarana <sa...@watson.ibm.com>.
> I'm running this question again because I still haven't found a solution,
but
> I did run into the same question from others.

Sorry for not repling earlier.

> Obviously there's more to it than meets the eye:

Yep.

> I'm building a SOAP interface for the financial (web) services of our
> company. Currently we offer just RMI.
>
> Ofcourse I want the SOAP interface to resemble the RMI interface as close as
> possible. As you'll understand we heavily rely on inherited classes that
> travel over the wire.
> In RMI this is all straightforward, but SOAP seems to be another story.

In Java object serialization the JVM is the one doing the serialization.
In a SOAP serializer, you have to explicitly write a serializer for
subclasses too because the serializer can only serialize stuff it knows
about and it doesn't know about the info in the subclass.

> I'll be using Apache-SOAP on the serverside. Since SOAP will be implemented
> on top of the existing RMI interface, I'll be writing my own serializers for
> our current return types.
>
> My question is how to implement these serializers if they need to serialize
> subclasses.
>
> Consider class A:
>
> public class A
> {
> private String param1;
>
> public A() {}
> public void setParam1(String param1) {
> this.param1 = param1;
> }
> public String getParam1() {
> return this.param1;
> }
> }
>
> and class B:
>
> public class B extends A
> {
> private String param2;
>
> public B() {}
> public void setParam2(String param2) {
> this.param2 = param2;
> }
> public String getParam2() {
> return this.param2;
> }
> }
>
> To serialize these, I figure I'd write ASerializer.java that will pretty
much
> resemble the simpler serializers in src/org/apache/soap/encoding/soapenc and
> I'd write BSerializer that extends ASerializer and marshalls the variables
in
> class B and then calls something like super.marshall().

Assuming you're interested in using SOAP encoding (section 5 of the
soap spec), the problem is that SOAP-enc doesn't support inheritance
and subclassing. As such, the subtype relationship cannot be
correctly represented in SOAP-enc without some assumptions on the
interpretation on the other side. That essentially amounts to
using a private encoding instead of soap-enc.

> Is that a correct solution? And what will the resulting xml envelope look
> like? What is the correct xml syntax of a serialized subclass anyway? Does

If you used your approach, here's what you'd get:

Say A looked like this (using soap-encoding):
    <A-xml>
        <param1>value-of-param1</param1>
    </A-xml>
then B's serialization would look like:
    <B-xml>
        <A-xml>
            <param1>value-of-param1</param1>
        </A-xml>
        <param2>value-of-param2</param2>
    </B-xml>

Is this "right"? If you interpret B-xml using the soap-enc rules then
B-xml is a struct with two fields; a complex one (called A-xml) and
a simple one (called param2). So you effectively lose the subtype
relationship.

> anyone know of examples of serializing inherited classes?

If you really want to maintain the subtype relationship across the
wire then you need to use a different encoding style.

> P.S. the reason that I won't be using the BeanSerializer for this example is
> that my real classes need special treatment and contain logic.

The BeanSerializer doesn't have the subtype problem because beans
are flat; they are not in type hierarchy.

> FYI, I have no clue what language/toolkit my clients will be using.

Then you really have no choice but use a non-subtype approach.

Sanjiva.


Re: Serializing inherited classes (2)

Posted by Sanjiva Weerawarana <sa...@watson.ibm.com>.
> I'm running this question again because I still haven't found a solution,
but
> I did run into the same question from others.

Sorry for not repling earlier.

> Obviously there's more to it than meets the eye:

Yep.

> I'm building a SOAP interface for the financial (web) services of our
> company. Currently we offer just RMI.
>
> Ofcourse I want the SOAP interface to resemble the RMI interface as close as
> possible. As you'll understand we heavily rely on inherited classes that
> travel over the wire.
> In RMI this is all straightforward, but SOAP seems to be another story.

In Java object serialization the JVM is the one doing the serialization.
In a SOAP serializer, you have to explicitly write a serializer for
subclasses too because the serializer can only serialize stuff it knows
about and it doesn't know about the info in the subclass.

> I'll be using Apache-SOAP on the serverside. Since SOAP will be implemented
> on top of the existing RMI interface, I'll be writing my own serializers for
> our current return types.
>
> My question is how to implement these serializers if they need to serialize
> subclasses.
>
> Consider class A:
>
> public class A
> {
> private String param1;
>
> public A() {}
> public void setParam1(String param1) {
> this.param1 = param1;
> }
> public String getParam1() {
> return this.param1;
> }
> }
>
> and class B:
>
> public class B extends A
> {
> private String param2;
>
> public B() {}
> public void setParam2(String param2) {
> this.param2 = param2;
> }
> public String getParam2() {
> return this.param2;
> }
> }
>
> To serialize these, I figure I'd write ASerializer.java that will pretty
much
> resemble the simpler serializers in src/org/apache/soap/encoding/soapenc and
> I'd write BSerializer that extends ASerializer and marshalls the variables
in
> class B and then calls something like super.marshall().

Assuming you're interested in using SOAP encoding (section 5 of the
soap spec), the problem is that SOAP-enc doesn't support inheritance
and subclassing. As such, the subtype relationship cannot be
correctly represented in SOAP-enc without some assumptions on the
interpretation on the other side. That essentially amounts to
using a private encoding instead of soap-enc.

> Is that a correct solution? And what will the resulting xml envelope look
> like? What is the correct xml syntax of a serialized subclass anyway? Does

If you used your approach, here's what you'd get:

Say A looked like this (using soap-encoding):
    <A-xml>
        <param1>value-of-param1</param1>
    </A-xml>
then B's serialization would look like:
    <B-xml>
        <A-xml>
            <param1>value-of-param1</param1>
        </A-xml>
        <param2>value-of-param2</param2>
    </B-xml>

Is this "right"? If you interpret B-xml using the soap-enc rules then
B-xml is a struct with two fields; a complex one (called A-xml) and
a simple one (called param2). So you effectively lose the subtype
relationship.

> anyone know of examples of serializing inherited classes?

If you really want to maintain the subtype relationship across the
wire then you need to use a different encoding style.

> P.S. the reason that I won't be using the BeanSerializer for this example is
> that my real classes need special treatment and contain logic.

The BeanSerializer doesn't have the subtype problem because beans
are flat; they are not in type hierarchy.

> FYI, I have no clue what language/toolkit my clients will be using.

Then you really have no choice but use a non-subtype approach.

Sanjiva.