2010-09-14 6 views
2

Je dois écrire un fichier WSDL sur un service Web existant qui me sera fourni par un collègue (réalisé avec Perl et SOAP :: Lite). Par conséquent, j'ai un format donné pour la réponse SOAP et j'ai besoin de définir formellement le service pour pouvoir générer le code pour un client Java au service. Pour tester le fichier WSDL par rapport au service, j'ai utilisé à la fois Web Service Explorer d'Eclipse et soapUI, pour générer le code pour le client. J'ai l'intention d'utiliser la version Axis distribuée avec Eclipse (1.3.x).Ecriture d'un fichier WSDL sur un service Web existant

Le fichier de définition que j'ai en ce moment fonctionne pour accéder au service via soapUI et renvoie la réponse SOAP souhaitée qui peut aussi être déclarée compatible avec Schema par soapUI, mais si je génère du code et tente d'exécuter le code, les choses commencent à s'effondrer. Apparemment, Axis ne reconnaît pas correctement les types définis et crée simplement des membres avec un type "anyType". La réponse ne peut donc pas être sérialisée correctement, ce qui entraîne une exception de la part de l'analyseur syntaxique SAX. Lorsque j'essaie de valider mon fichier WSDL, on me dit qu'il n'est pas permis de définir un élément avec juste un autre élément en tant qu'enfant, ce qui, je suppose, est la racine de mes problèmes ici. J'ai essayé d'imbriquer l'élément "prefix_map" dans un complexType anonyme en tant qu'élément unique d'une séquence, mais maintenant l'assertion de conformité de schéma dans soupUI échoue. Alors, comment puis-je définir correctement les types pour le message de réponse pour la réponse donnée?

C'est le SOAP-réponse que je reçois du service:

<SOAP-ENV:Envelope SOAP-ENV:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/" xmlns:xsi="http://www.w3.org/1999/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/1999/XMLSchema"> 
    <SOAP-ENV:Body> 
    <namesp1:get_dest_prefixResponse xmlns:namesp1="PortaTAPI"> 
     <prefix_map> 
      <country xsi:type="xsd:string">SWITZERLAND</country> 
      <iso_3166_1_a2 xsi:type="xsd:string">CH</iso_3166_1_a2> 
      <i_group xsi:type="xsd:int">0</i_group> 
      <destination xsi:type="xsd:long">41445551234</destination> 
      <i_env xsi:type="xsd:int">2</i_env> 
      <i_dest xsi:type="xsd:int">10007</i_dest> 
      <description xsi:type="xsd:string">Customer AG - Wholesale</description> 
      <i_country_subdivision xsi:type="xsd:int">2855</i_country_subdivision> 
      <dest_type xsi:null="1"/> 
      <i_time_zone xsi:null="1"/> 
     </prefix_map> 
    </namesp1:get_dest_prefixResponse> 
    </SOAP-ENV:Body> 
</SOAP-ENV:Envelope> 

Ceci est la partie pertinente de mon fichier WSDL:

<?xml version="1.0" encoding="UTF-8" standalone="no"?> 
<wsdl:definitions 
    name="PortaTAPI" 
    targetNamespace="PortaTAPI" 
    xmlns:tns="PortaTAPI" 
    xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/" 
    xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/" 
    xmlns:xsd="http://www.w3.org/2001/XMLSchema"> 

    <!-- Type Definitions --> 
    <wsdl:types> 
    <xsd:schema targetNamespace="PortaTAPI"> 

    <xsd:complexType name="t_prefix_map"> 
    <xsd:all> 
     <xsd:element name="country" type="xsd:string" minOccurs="1" /> 
     <xsd:element name="iso_3166_1_a2" type="xsd:string" minOccurs="1" /> 
     <xsd:element name="i_group" type="xsd:int" minOccurs="1" /> 
     <xsd:element name="destination" type="xsd:long" minOccurs="1" /> 
     <xsd:element name="i_env" type="xsd:int" minOccurs="1" /> 
     <xsd:element name="i_dest" type="xsd:int" minOccurs="1" /> 
     <xsd:element name="description" type="xsd:string" minOccurs="0" /> 
     <xsd:element name="i_country_subdivision" type="xsd:int" minOccurs="1" /> 
     <xsd:element name="dest_type" type="xsd:string" nillable="true" minOccurs="0" /> 
     <xsd:element name="i_time_zone" type="xsd:string" nillable="true" minOccurs="0" /> 
    </xsd:all> 
    </xsd:complexType> 

    <xsd:complexType name="t_tariff_map"> 
    <xsd:all> 
     <xsd:element name="i_tariff" type="xsd:int"/> 
    </xsd:all> 
    </xsd:complexType> 


    <xsd:element name="get_dest_prefix"> 
    <xsd:complexType> 
     <xsd:all> 
     <xsd:element name="prefix" type="xsd:long" minOccurs="1" /> 
     <xsd:element name="i_env" type="xsd:int" minOccurs="1" /> 
     </xsd:all> 
    </xsd:complexType> 
    </xsd:element> 
    <xsd:element name="get_dest_prefixResponse"> 
    <xsd:element name="prefix_map" type="tns:t_prefix_map" /> 
    </xsd:element> 
    <!-- This causes the Schema compliance assertion of soapUI to fail 
    <xsd:element name="get_dest_prefixResponse"> 
    <xsd:complexType> 
     <xsd:sequence> 
     <xsd:element name="prefix_map" type="tns:t_prefix_map" /> 
     </xsd:sequence> 
    </xsd:complexType> 
    </xsd:element> 
    --> 

    </xsd:schema> 
    </wsdl:types> 

    <!-- Messages --> 
    <wsdl:message name="get_dest_prefixRequest"> 
    <wsdl:part name="parameters" element="tns:get_dest_prefix" /> 
    </wsdl:message> 
    <wsdl:message name="get_dest_prefixResponse"> 
    <wsdl:part name="result" element="tns:get_dest_prefixResponse" /> 
    </wsdl:message> 

    <!-- Port --> 
    <wsdl:portType name="PortaTAPI"> 

    <wsdl:operation name="get_dest_prefix"> 
    <wsdl:input message="tns:get_dest_prefixRequest" /> 
    <wsdl:output message="tns:get_dest_prefixResponse" /> 
    </wsdl:operation> 

    </wsdl:portType> 

    <!-- Bindings --> 
    <wsdl:binding name="PortaTAPISOAP" type="tns:PortaTAPI"> 
    <soap:binding style="document" transport="http://schemas.xmlsoap.org/soap/http" /> 

    <wsdl:operation name="get_dest_prefix"> 
    <soap:operation soapAction="PortaTAPI#get_dest_prefix" /> 
    <wsdl:input> 
    <soap:body use="literal" /> 
    </wsdl:input> 
    <wsdl:output> 
    <soap:body use="literal" /> 
    </wsdl:output> 
    </wsdl:operation> 

    </wsdl:binding> 

    <!-- Service --> 
    <wsdl:service name="PortaTAPI"> 
    <wsdl:port binding="tns:PortaTAPISOAP" name="PortaTAPISOAP"> 
    <soap:address location="https://62.65.137.91:3113/soap.pl" /> 
    </wsdl:port> 
    </wsdl:service> 

</wsdl:definitions> 

C'est l'exception du client (généré par Axis) jette:

Sep 14, 2010 2:22:28 PM org.apache.axis.client.Call invoke 
SEVERE: Exception: 
org.xml.sax.SAXException: Deserializing parameter 'get_dest_prefixResponse': could not find deserializer for type {http://www.w3.org/2001/XMLSchema}anyType 
    at org.apache.axis.message.RPCHandler.onStartChild(RPCHandler.java:277) 
    at org.apache.axis.encoding.DeserializationContext.startElement(DeserializationContext.java:1035) 
    at org.apache.axis.message.SAX2EventRecorder.replay(SAX2EventRecorder.java:165) 
    at org.apache.axis.message.MessageElement.publishToHandler(MessageElement.java:1141) 
    at org.apache.axis.message.RPCElement.deserialize(RPCElement.java:236) 
    at org.apache.axis.message.RPCElement.getParams(RPCElement.java:384) 
    at org.apache.axis.client.Call.invoke(Call.java:2467) 
    at org.apache.axis.client.Call.invoke(Call.java:2366) 
    at org.apache.axis.client.Call.invoke(Call.java:1812) 
    at com.netstream.ch.porta.tapi.PortaTAPISOAPStub.get_dest_prefix(PortaTAPISOAPStub.java:261) 
    at com.netstream.ch.porta.services.DestinationManagementService.getDestination(DestinationManagementService.java:49) 
    at com.netstream.ch.porta.PortaServicesTest.actionPerformed(PortaServicesTest.java:219) 
    at javax.swing.AbstractButton.fireActionPerformed(AbstractButton.java:1995) 
    at javax.swing.AbstractButton$Handler.actionPerformed(AbstractButton.java:2318) 
    at javax.swing.DefaultButtonModel.fireActionPerformed(DefaultButtonModel.java:387) 
    at javax.swing.DefaultButtonModel.setPressed(DefaultButtonModel.java:242) 
    at javax.swing.plaf.basic.BasicButtonListener.mouseReleased(BasicButtonListener.java:236) 
    at java.awt.Component.processMouseEvent(Component.java:6263) 
    at javax.swing.JComponent.processMouseEvent(JComponent.java:3267) 
    at java.awt.Component.processEvent(Component.java:6028) 
    at java.awt.Container.processEvent(Container.java:2041) 
    at java.awt.Component.dispatchEventImpl(Component.java:4630) 
    at java.awt.Container.dispatchEventImpl(Container.java:2099) 
    at java.awt.Component.dispatchEvent(Component.java:4460) 
    at java.awt.LightweightDispatcher.retargetMouseEvent(Container.java:4574) 
    at java.awt.LightweightDispatcher.processMouseEvent(Container.java:4238) 
    at java.awt.LightweightDispatcher.dispatchEvent(Container.java:4168) 
    at java.awt.Container.dispatchEventImpl(Container.java:2085) 
    at java.awt.Window.dispatchEventImpl(Window.java:2478) 
    at java.awt.Component.dispatchEvent(Component.java:4460) 
    at java.awt.EventQueue.dispatchEvent(EventQueue.java:599) 
    at java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:269) 
    at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:184) 
    at java.awt.EventDispatchThread.pumpEventsForHierarchy(EventDispatchThread.java:174) 
    at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:169) 
    at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:161) 
    at java.awt.EventDispatchThread.run(EventDispatchThread.java:122) 
AxisFault 
faultCode: {http://schemas.xmlsoap.org/soap/envelope/}Server.userException 
faultSubcode: 
faultString: org.xml.sax.SAXException: Deserializing parameter 'get_dest_prefixResponse': could not find deserializer for type {http://www.w3.org/2001/XMLSchema}anyType 
faultActor: 
faultNode: 
faultDetail: 
    {http://xml.apache.org/axis/}stackTrace:org.xml.sax.SAXException: Deserializing parameter 'get_dest_prefixResponse': could not find deserializer for type {http://www.w3.org/2001/XMLSchema}anyType 

Merci pour votre aide!

Répondre

1

Ok. Après avoir commenté ci-dessous j'ai affiné ma réponse. Je crois qu'Axis cherche un type concret pour l'élément en question. Comme il n'est pas défini, il suppose que c'est anyType, avec lequel il a du mal à trouver. Je voudrais faire ce qui suit:

<xsd:element name="get_dest_prefix"> 
<xsd:complexType> 
    <xsd:all> 
    <xsd:element name="prefix" type="xsd:long" minOccurs="1" /> 
    <xsd:element name="i_env" type="xsd:int" minOccurs="1" /> 
    </xsd:all> 
</xsd:complexType> 
</xsd:element> 
<xsd:element name="get_dest_prefixResponse" type="tns:t_get_dest_prefixResponse"/> 
<xsd:complexType name="t_get_dest_prefixResponse"> 
    <xsd:sequence> 
    <xsd:element name="prefix_map" type="tns:t_prefix_map" minOccurs="1"/> 
    </xsd:sequence> 
</xsd:complexType> 

Cela a-t-il aidé? Cela pourrait le rendre plus explicite et permettre à Axis de trouver ce qu'il veut.

+0

Le problème semble être qu'il n'est pas permis de définir un élément directement dans un autre élément, comme j'ai essayé de le faire avec l'élément "get_dest_prefixResponse" qui contient l'élément "prefix_map". D'après ma compréhension de WSDL, je pense que cela ne devrait faire aucune différence si je définis le schéma pour les types en ligne comme XSD ou dans un fichier XSD séparé. J'ai dû créer le fichier WSDL à la main depuis l'enveloppe SOAP car SOAP: Lite n'en a apparemment pas besoin et, comme Perl est dynamiquement typé, mon collègue ne pouvait pas me dire les types exacts de ses réponses. – wtfc63

+0

Cela a aidé :-) Bien que l'assertion de conformité de schéma dans soapUI échoue maintenant, Axis est capable de générer des classes pour un client qui, d'après son apparence, interagit correctement avec le service. Merci beaucoup pour votre aide! – wtfc63

Questions connexes