1 Reply Latest reply on Dec 27, 2006 11:46 PM by guurk

    Collection in java -> wsdl for wstools

    guurk

      JSR-181 deploying a ejb3 stateless as a web service using JBossIDE.

      JBoss 4.0.5.GA
      JBossIDE 2.0.0 Beta 2
      JDK 1.5.0_08

      On a method:

      @javax.jws.WebMethod()
      public Collection<News> getNews() {
      }
      


      where News is an ejb3 entity bean (complex type):

      @Entity
      @Table( name = "news", uniqueConstraints = {})
      public class News implements java.io.Serializable {
       // Fields
       private static final long serialVersionUID = 1L;
       private Long id;
       private String title;
       private String description;
       private String body;
       private String author;
       private Set< RssItem> rssItems = new HashSet< RssItem>( 0);
      ...
      ...
      ...
      


      The WSDL generated does not contain a sequence with the complex type defined:

       <complexType name="Collection">
       <sequence>
       <element name="empty" type="boolean" />
       </sequence>
       </complexType>
       <complexType name="News">
       <sequence>
       <element name="author" nillable="true" type="string" />
       <element name="body" nillable="true" type="string" />
       <element name="description" nillable="true" type="string" />
       <element name="id" nillable="true" type="long" />
       <element name="title" nillable="true" type="string" />
       </sequence>
       </complexType>
       </schema>
      
       <message name="ResonusBE_getNewsResponse">
       <part name="result" type="tns:Collection" />
       </message>
      
      <message name="ResonusBE_getNews" />
      
       <operation name="getNews">
       <input message="tns:ResonusBE_getNews" />
       <output message="tns:ResonusBE_getNewsResponse" />
       </operation>
      
      


      Notice that the collection specified for Collection is collection with a boolen... not even close to the right type.

      The News complex type only shows up in the WSDL if I explicitly have another method that returns News. It won't show up if it's just with in the Collection generics.

      For testing purposes I tried out the XFire java->wsdl libraries... it does a nice job:

       <xsd:complexType name="ArrayOfNews">
       <xsd:sequence>
       <xsd:element maxOccurs="unbounded" minOccurs="0" name="News" nillable="true" type="tns:News" />
       </xsd:sequence>
       </xsd:complexType>
       <xsd:complexType name="News">
       <xsd:sequence>
       <xsd:element minOccurs="0" name="author" nillable="true" type="xsd:string" />
       <xsd:element minOccurs="0" name="body" nillable="true" type="xsd:string" />
       <xsd:element minOccurs="0" name="description" nillable="true" type="xsd:string" />
       <xsd:element minOccurs="0" name="id" nillable="true" type="xsd:long" />
       <xsd:element minOccurs="0" name="title" nillable="true" type="xsd:string" />
       </xsd:sequence>
       </xsd:complexType>
      


      Thoughts? Am I missing something?



        • 1. Re: Collection in java -> wsdl for wstools
          guurk

          Ok, I've gone through the Axis website which it appears the wstools is based on. Based on the documentation there, there is no 'proper' way to do collections, it's really up to the implementer..

          From http://ws.apache.org/axis/java/user-guide.html#HowYourJavaTypesMapToSOAPXMLTypes


          Java Collections
          Some of the Collection classes, such as Hashtable, do have serializers, but there is no formal interoperability with other SOAP implementations, and nothing in the SOAP specifications which covers complex objects. The most reliable way to send aggregate objects is to use arrays. In particular, .NET cannot handle them, though many Java SOAP implementations can marshall and unmarshall hash tables.


          Thus, I changed my method signature, and instead of returning Collection I changed it to return News[]. An array.

          This produced much better results in the generated WSDL.

          <complexType name="News">
          - <sequence>
           <element name="author" nillable="true" type="string" />
           <element name="body" nillable="true" type="string" />
           <element name="description" nillable="true" type="string" />
           <element name="id" nillable="true" type="long" />
           <element name="title" nillable="true" type="string" />
           </sequence>
           </complexType>
          - <complexType name="News.Array">
          - <sequence>
           <element maxOccurs="unbounded" minOccurs="0" name="value" nillable="true" type="ns10:News" />
           </sequence>
           </complexType>
          


          Very much in order with what I was looking for.

          Bottom Line

          Use arrays instead of gerisized Collections.