How sad.. that nobody in Apache Soap Development community has the GUTS to
acknowledge that either it is a bug or not a bug in Soap 2.2 BeanSerializer.
Why should
Soap 2.2 BeanSerialize run out of stack depth if class Employee contains a
field 'subordinates'
of type Employee[] or Vector of Employee?
What purpose [EMAIL PROTECTED] serves if I am not able to get answer
to this technical question from
so called experts?
Could anybody please suggest suitable forums where I may post technical
question such as this regarding
APACHE SOAP 2.2?
Thanks in advance to anybody kind enough to reply.
Regards,
Soumen.
> -----Original Message-----
> From: Soumen Sarkar
> Sent: Monday, July 09, 2001 11:11 AM
> To: '[EMAIL PROTECTED]'
> Subject: Bugs in Soap 2.2 BeanSerializer?
>
> Hi,
>
> I tried to exchange the following data structure over SOAP by using SOAP
> 2.2 Bean Serializer class
> public class Employee implements Serializable
> {
> // not null
> public String name;
> // null if no manager
> public Employee manager;
> // null if no subordinates,this is a Employee Vector
> public Vector subordinates;
> }
> It runs into the following serialization problem:
> <stackTrace>
> <detail>
> java.lang.StackOverflowError
> at java.lang.Class.toString(Class.java:82)
> at java.lang.String.valueOf(String.java:1925)
> at
> org.apache.soap.util.xml.XMLJavaMappingRegistry.getKey(XMLJavaMappingRegis
> try.java:265)
> at
> org.apache.soap.util.xml.XMLJavaMappingRegistry.queryElementType(XMLJavaMa
> ppingRegistry.java:192)
> at
> org.apache.soap.encoding.SOAPMappingRegistry.queryElementType(SOAPMappingR
> egistry.java:460)
> at
> org.apache.soap.encoding.soapenc.SoapEncUtils.generateStructureHeader(Soap
> EncUtils.java:129)
> at
> org.apache.soap.encoding.soapenc.SoapEncUtils.generateStructureHeader(Soap
> EncUtils.java:116)
> at
> org.apache.soap.encoding.soapenc.BeanSerializer.marshall(BeanSerializer.ja
> va:86)
> at
> org.apache.soap.util.xml.XMLJavaMappingRegistry.marshall(XMLJavaMappingReg
> istry.java:238)
> at
> org.apache.soap.encoding.soapenc.ArraySerializer.marshall(ArraySerializer.
> java:133)
> ......
> ......
> ......
> at
> org.apache.soap.encoding.soapenc.BeanSerializer.marshall(BeanSerializer.ja
> va:131)
> </stackTrace>
> </detail>
> </SOAP-ENV:Fault>
>
> Basically I found out that SOAP 2.2 BeanSerializer can not handle Employee
> class having
> subordinate field as a Vector of Employee (or Employee[]). When I shanged
> subordinates field
> to Vector of String (or String[]) there was no StackOverflow problem.
> There is no problem in
> exchanging this data structure over EJB (i.e Java RMI). I also found out
> that SOAP 2.2 XML
> serialization does not implement reference semantics as it is done in
> basic Java/RMI serialization.
> What this means is that XML messages tend to be very large in situations
> where Employee contains
> reference to another Employee(i.e manager). What SOAP 2.2 BeanSerializer
> does is to LITERALLY
> INCLUDE ALL DETAILS OF MANAGER in EACH SUBORDINATE OF THAT MANAGER.
> This is very naive implementation and will cause very large XML messages.
> XML permits ID, IDERF,
> why not use that? Why to literally REPEAT Manager details in each
> Employee?
>
> Can somebody from SOAP development team confirm that these are indeed
> BeanSerializer bug/shortcomings?
> I am attaching complete Employee class below.
>
> Regards,
> Soumen Sarkar
>
> Atoga Systems Inc. (http://www.atoga.com)
> 510-743-0254
>
> Employee class
> ------------------------
> //Writing Employee as an ideal bean by providing get and set methods
> package AnotherEmployeeSLBean;
> import java.io.*;
> import java.util.*;
> public class Employee implements Serializable
> {
> // not null
> public String name;
> // null if no manager
> public Employee manager;
> // null if no subordinates,this is a Employee Vector
> public Vector subordinates;
> // not null
> public String ssn;
> public double salary;
> // null if no dependents
> public Dependent[] dependents;
> public Employee()
> { }
> public Employee(String name,Employee manager,Employee[]
> subordinates,String ssn,double salary,Dependent[] dependents)
> { this.name = name;
> this.manager = manager;
> this.subordinates = subordinates;
> this.ssn = ssn;
> this.salary = salary;
> this.dependents = dependents;
> }
> public String getName() { return name; }
> public void setName(String name) { this.name = name; }
> public Employee getManager() { return manager; }
> public void setManager(Employee manager) { this.manager = manager; }
> public Vector getSubordinates() { return subordinates; }
> public void setSubordinates(Vector subordinates) { this.subordinates =
> subordinates; }
> public String getSsn() { return ssn; }
> public void setSsn(String ssn) { this.ssn = ssn; }
> public double getSalary() { return salary; }
> public void setSalary(double salary) { this.salary = salary; }
> public Dependent[] getDependents() { return dependents; }
> public void setDependents(Dependent[] dependents) { this.dependents =
> dependents; }
> public String toString()
> { String retVal = "Employee" + "\n"; retVal += "{" + "\n";
> retVal += "name = " + name + "\n";
> retVal += "ssn = " + ssn + "\n";
> retVal += "salary = " + salary + "\n";
> retVal += "manager = " + manager + "\n";
> if(subordinates!= null)
> { retVal += "Subordinates are:";
> for(int i = 0; i < subordinates.size(); ++i)
> { retVal += subordinates.elementAt(i)+ "\n"; }
> }
> if(dependents!= null)
> { retVal += "Dependents are:";
> for(int i = 0; i < dependents.length; ++i) { retVal += dependents[i]+
> "\n"; }
> }
> retVal += "}" + "\n"; return retVal;
> }
> }
> //Writing Dependent as an ideal bean by providing get and set methods
> package AnotherEmployeeSLBean;
> import java.io.*;
> public class Dependent implements Serializable
> {
> public String name;
> public int age;
> public String relationship;
> public Dependent(String name,int age,String relationship)
> { this.name = name; this.age = age; this.relationship = relationship; }
> public Dependent() { }
> public String getName() { return name; }
> public void setName(String name) { this.name = name; }
> public int getAge() { return age; }
> public void setAge(int age) { this.age = age; }
> public String getRelationship() { return relationship; }
> public void setRelationship(String relationship) { this.relationship =
> relationship; }
> public String toString()
> { String retVal = "Dependent" + "\n";
> retVal += "{" + "\n";
> retVal += "name = " + name + "\n";
> retVal += "age = " + age + "\n";
> retVal += "relationship = " + relationship + "\n";
> retVal += "}" + "\n"; return retVal;
> }
> }