Suche…


Bemerkungen

In diesem Abschnitt erhalten Sie einen Überblick darüber, was Seife ist und warum ein Entwickler sie verwenden möchte.

Es sollte auch alle großen Themen in Seife erwähnen und auf die verwandten Themen verweisen. Da die Dokumentation für Seife neu ist, müssen Sie möglicherweise erste Versionen dieser verwandten Themen erstellen.

Versionen

Ausführung Veröffentlichungsdatum
1.1 2000-05-08
1.2 2003-06-24

Allgemeine Information

SOAP ist eine Abkürzung für Simple Object Access Protocol (Simple Object Access Protocol) , das ein Protokoll definiert, mit dem Daten über einen Remote Procedure Call (RPC) mit anderen SOAP-Diensten oder -Clients ausgetauscht werden. Es ist in zwei Versionen erhältlich:

SOAP 1.2 ersetzt SOAP 1.1. Es wird daher empfohlen, SOAP 1.2 nach Möglichkeit zu verwenden.

Es wird oft auf HTTP / S aufgebaut und selten auf SMTP oder FTP, obwohl es es entsprechend dem Protokoll unterstützen würde. Obwohl HTTP häufig als zugrunde liegendes Transportprotokoll verwendet wird, verwendet SOAP nur eine begrenzte Teilmenge davon. Für das Senden von Anforderungen ist der POST Vorgang von HTTP fast vollständig erforderlich. GET Aufrufe sind theoretisch seit 1.2 möglich, obwohl das Dokument als URI-Parameter übergeben werden muss und daher eine Grenze von etwa 3000 Zeichen überschreiten kann, die von den meisten Frameworks abgelehnt wird. Sicherheitsbezogene Einstellungen werden normalerweise auch in einem speziellen SOAP-Header definiert.

Obwohl SOAP und REST als Web-Services bezeichnet werden, unterscheiden sie sich naturgemäß sehr. Einige Frameworks unterscheiden zwischen WS (für SOAP-basierte Dienste) und RS (für REST-basierte Dienste).

Die folgende Tabelle gibt einen kurzen Überblick über die Unterschiede zwischen den beiden Web-Service-Typen.

Aspekt SEIFE SICH AUSRUHEN
Standard SOAP , WSDL Kein Standard, nur ein architektonischer Stil
Adressierung von Ressourcen Indirekt über SOAP-Operationen über eindeutige Ressourcenkennungen (URIs)
Fehlerbehandlung SOAP-Fehlermeldung HTTP-Fehlerantwortcodes und optionaler Antworttext
Daten Präsentation XML alle verfügbaren Kodierungen in HTTP
HTTP-Verwendung Als Transportprotokoll Aktionen für Ressourcen (CRUD), die HTTP-Methoden zugeordnet sind (GET, POST, PUT, DELETE, ...)
Transaktionsunterstützung über den SOAP-Header durch Modellieren einer Transaktion als Ressource
Zustand Stateful (SOAP-Aktion ist Teil der Anwendung) Zustandslos (in sich geschlossene Anfragen)
Service Discovery UDDI / WSDL Eigentlich nicht; Start-URI der API sollte jedoch eine Liste von Unter-APIs zurückgeben
Methode Im SOAP-Körper HTTP-Methode
Methodenargumente Definiert durch XML-Schema in der WSDL Entweder über HTTP-Header oder Path / Query- oder Matrix-Parameter innerhalb der URI
Zustandsübergang Schwer zu bestimmen, da nicht direkt auf Daten basiert Nächster URI-Aufruf
Caching-Unterstützung Caching oft nicht erwünscht, Einfach wie von HTTP definiert

SEIFE

Eine SOAP-Anforderung besteht aus einem SOAP-Envelop, der ein body-Element und ein optionales Header-Element enthalten muss. Das Header-Element wird verwendet, um bestimmte Konfigurationen an den Dienst zu übergeben, z. B. WS-Security kann definieren, dass die Nachricht verschlüsselt ist, oder WS-Coordination / WS-Transaction kann definieren, dass die Nachricht innerhalb einer Transaktion ausgeführt werden muss.

Eine einfache SOAP 1.2-Anforderung über HTTP, die zwei Werte hinzufügt, kann folgendermaßen aussehen:

POST /calculator HTTP/1.1
Host: http://example.org
Content-Type: application/soap+xml; charset=utf-8
Content-Length: 224

<?xml version="1.0"?>
<env:Envelope xmlns:env="http://www.w3.org/2003/05/soap-envelope">
 <env:Body>
  <m:AddValues xmlns:m="http://example.org/calculator">
   <m:FirstValue>1</m:FirstValue>
   <m:SecondValue>2</m:SecondValue>
  </m:AddValues>
 </env:Body>
</env:Envelope>

Eine Antwort auf die obige Beispielanfrage kann so aussehen

HTTP/1.1 200 OK
Content-Type: application/soap+xml; charset=utf-8
Content-Length: 329

<?xml version="1.0"?>
<soap:Envelope xmlns:soap="http://www.w3.org/2003/05/soap-envelope"
               soap:encodingStyle="http://www.w3.org/2003/05/soap-encoding">
 <soap:Body xmlns:m="http://www.example.org/calculator">
  <m:AddValuesResponse>
   <m:Result>3</m:Result>
  </m:AddValuesResponse>
 </soap:Body>
</soap:Envelope>

Im obigen Beispiel wurde eine Anforderung definiert, die die AddValues Methode mit den zwei Argumenten FirstValue auf 1 und SecondValue auf 2 SecondValue . Die Anforderung führte zu einer Ausführung dieser Methode auf dem Remote-SOAP-Server, der als Ergebnis einen Wert von 3 berechnet hat, der in einem separaten Antwortelement gekapselt wird. Dies ist in der Regel der aufgerufene Methodenname plus einer nachgestellten Response Durch Überprüfen der Antwort kann festgestellt werden, dass dies die Antwort eines vorherigen AddValue Methode ist.

Unterschiede zwischen SOAP 1.1 und 1.2

SOAP 1.2 erlaubt andere Transportprotokolle als HTTP, sofern das Bindungsframework vom Protokoll unterstützt wird.

SOAP 1.1 basiert auf XML 1.0, während 1.2 auf XML Infoset basiert, mit dem die SOAP-Nachrichten mit anderen Serialisierern als mit dem von SOAP 1.1 verwendeten Standard-XML 1.0-Serialisierer serialisiert werden können. Dies ermöglicht beispielsweise das Serialisieren von Nachrichten als binäre Nachrichten und somit einen gewissen Aufwand für die XML-Natur der Nachricht. Darüber hinaus kann der Serialisierungsmechanismus des zugrunde liegenden Protokolls über die Datenbindung bestimmt werden.

Der Aspekt der Interoperabilität wurde auch mit SOAP 1.2 gefördert, indem ein spezifischeres Verarbeitungsmodell als sein Vorgänger definiert wurde, wodurch viele Interpretationsmöglichkeiten beseitigt wurden. SOAP with Attachment API (SAAJ), das den Betrieb von SOAP 1.1- und 1.2-Nachrichten ermöglicht, half vielen Framework-Implementatoren, Nachrichten zu verarbeiten und zu erstellen.

Das W3C hat einen kurzen Überblick über die wichtigsten Änderungen zwischen SOAP 1.1 und 1.2 veröffentlicht

Web-Service-Interoperabilität

Web Service Interoperability (auch als WS-I bezeichnet) ist eine Interoperabilitätsrichtlinie, die von einigen bekannten Unternehmen wie IBM, Microsoft, Oracle und HP geregelt wird, um nur einige zu nennen. In diesen Richtlinien wird unter anderem empfohlen, nur ein einziges Stammelement innerhalb des SOAP-Rumpfs zu verwenden, auch wenn der SOAP die Verwendung mehrerer Elemente im Rumpf zulässt.

WS-I besteht aus

  • WS-I-Basisprofil aka WSI-BP
  • WS-I Grundlegendes Sicherheitsprofil
  • Einfaches Seifenbindungsprofil

WSI-BP ist in 4 verschiedenen Versionen v1.0 (2004) , v1.1 (2006) , v1.2 (2010) , v2.0 (2010) verfügbar und definiert Interoperabilitätsrichtlinien für Kernwebdienstspezifikationen wie SOAP, WSDL und UDDI. Durch die Verwendung von WSDL (Web Services Description Language) können SOAP-Dienste ihre unterstützten Operationen und Methoden innerhalb eines zusammenhängenden Satzes für andere Endpunkte beschreiben. WSI-BP verwendet WSDL, um ein engeres Set zu definieren, als das vollständige WSDL- oder SOAP-Schema definieren würde. Dadurch wird ein Teil der Mehrdeutigkeit innerhalb der Spezifikation selbst beseitigt und somit die Interoperabilität zwischen Endpunkten verbessert.

WSDL

Um die verfügbaren SOAP-Operationen, ihre Parameter sowie die jeweiligen Endpunkte zum Aufruf an Clients anzukündigen, wird ein weiteres XML-basiertes Dokument verwendet, das als Web Services Description Language oder kurz WSDL bezeichnet wird.

WSDL beschreibt den Serviceendpunkt, das Binden von SOAP-Nachrichten an Operationen, die Schnittstelle der Operationen sowie deren Typen an Clients. WSDL ist wie SOAP in 2 Versionen verfügbar, die sich in ihrer Syntax leicht unterscheiden, jedoch dem Client fast dieselbe Semantik ausdrücken.

WSDL 1.1

Eine WSDL 1.1-Beschreibung enthält einen service , eine binding , einen portType und einen message . Es kann weiter Schemas innerhalb der WSDL-Datei importieren oder definieren, wie aus einer WSDL-Beispieldatei ersichtlich ist, die dem oben gezeigten Taschenrechner-Beispiel entspricht:

<wsdl:definitions xmlns:xs="http://www.w3.org/2001/XMLSchema"
                  xmlns:http="http://schemas.xmlsoap.org/wsdl/http/"
                  xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
                  xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"
                  xmlns:calc="http://example.org/calculator"
                  xmlns:tns="http://example.org/calculatorService"
                  targetNamespace="http://example.org/calculatorService">

    <!--
      Abstract type definitions
    -->

    <wsdl:types>
        <!--
        <xs:schema>
            <xs:import namespace="http://example.org/calculator" schemaLocation="calc/calculator.xsd" />
        </xs:schema>
        -->
        <xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema"
                   xmlns:tns="http://example.org/calculator"
                   targetNamespace="http://example.org/calculator"
                   elementFormDefault="qualified"
                   attributeFormDefault="qualified">

            <xs:element name="AddValuesRequest" type="tns:AddValuesType" />
            <xs:element name="AddValuesResponse" type="tns:AddValuesResponseType" />

            <xs:complexType name="AddValuesType">
                <xs:sequence>
                    <xs:element name="FirstValue" type="xs:int" minOccurs="1" maxOccurs="1" />
                    <xs:element name="SecondValue" type="xs:int" minOccurs="1" maxOccurs="1" />
                </xs:sequence>
            </xs:complexType>

            <xs:complexType name="AddValuesResponseType">
                <xs:sequence minOccurs="1" maxOccurs="1">
                    <xs:element name="Result" type="xs:int" />
                </xs:sequence>
            </xs:complexType>

            <xs:attribute name="Timestamp" type="xs:dateTime" />
            <xs:element name="CalculationFailure">
                <xs:complexType>
                    <xs:sequence>
                        <xs:element name="ErrorCode" type="xs:int" />
                        <xs:element name="Reason" type="xs:string" />
                    </xs:sequence>
                    <xs:attribute ref="tns:Timestamp" use="required" />
                </xs:complexType>
            </xs:element>

        </xs:schema>
    </wsdl:types>

    <!--
        Abstract message definitions
    -->

    <wsdl:message name="AddValuesRequest">
        <wsdl:part name="in" element="calc:AddValuesRequest" />
    </wsdl:message>
    <wsdl:message name="AddValuesResponse">
        <wsdl:part name="out" element="calc:AddValuesResponse" />
    </wsdl:message>
    <wsdl:message name="CalculationFault">
        <wsdl:part name="fault" element="calc:CalculationFailure" />
    </wsdl:message>

    <!--
        Abstract portType / interface definition
    -->

    <wsdl:portType name="CalculatorEndpoint">
        <wsdl:operation name="AddValues">
            <wsdl:documentation>Adds up passed values and returns the result</wsdl:documentation>
            <wsdl:input message="tns:AddValuesRequest" />
            <wsdl:output message="tns:AddValuesResponse" />
            <wsdl:fault name="CalculationFault" message="tns:CalculationFault" />
        </wsdl:operation>
    </wsdl:portType>

    <!--
      Concrete binding definition
    -->

    <wsdl:binding name="CalculatorBinding" type="tns:CalculatorEndpoint">
        <soap:binding style="document" transport="http://schemas.xmlsoap.org/soap/http"/>
        <wsdl:operation name="AddValues">
            <soap:operation soapAction="http://example.org/calculator/AddValuesMessage" />
            <wsdl:input>
                <soap:body parts="in" use="literal" />
            </wsdl:input>
            <wsdl:output>
                <soap:body parts="out" use="literal" />
            </wsdl:output>
            <wsdl:fault name="CalculationFault">
                <soap:fault name="CalculationFault" use="literal" />
            </wsdl:fault>
        </wsdl:operation>
    </wsdl:binding>

    <!--
        Concrete service definition
    -->

    <wsdl:service name="CalculatorService">
        <wsdl:port name="CalculatorServicePort" binding="tns:CalculatorBinding">
            <soap:address location="http://localhost:8080/services/calculator" />
        </wsdl:port>
    </wsdl:service>

</wsdl:definitions>

Ein service definiert die konkreten Endpunkte, die der Service auf eingehende Anforderungen überwacht. Der binding bindet eine Operation an einen konkreten Stil und definiert, welche Nachrichtenformate der Server erwartet oder was der Client erwarten kann.

Der abstrakte Abschnitt besteht aus einem portType Block, der die vom Dienst angebotenen portType definiert und welche Nachrichten ausgetauscht werden. Die Nachrichten werden in ihrem On-Block angegeben und mit den Schematypen verknüpft, für die die Argumente und Rückgabewerte Instanzen sind. Nachrichten können Parameter deklarieren oder Werte als inout , out oder in out inout . Während die ersten beiden recht einfach zu erfassen sind, ahmen die letzteren das Verhalten von Argumenten nach, die als Referenz übergeben werden. Da Pass-by-Ref in einigen Sprachen nicht unterstützt wird, wird dieser Effekt häufig über bestimmte Handler simuliert.

WSDL 2.0

Derselbe Rechner kann in WSDL 2.0 folgendermaßen beschrieben werden:

<?xml version="1.0" encoding="utf-8" ?>
<wsdl:description xmlns:xs="http://www.w3.org/2001/XMLSchema"
                  xmlns:wsdl="http://www.w3.org/ns/wsdl"
                  xmlns:soap="http://www.w3.org/ns/wsdl/soap"
                  xmlns:calc="http://example.org/calculator"
                  xmlns:tns="http://example.org/calculatorService"
                  targetNamespace="http://example.org/calculatorService">

    <!--
      Abstract type definitions
    -->

    <wsdl:types>
        <!--
        <xs:schema>
            <xs:import namespace="http://example.org/calculator" schemaLocation="calc/calculator.xsd" />
        </xs:schema>
        -->
        <xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema"
                   xmlns:tns="http://example.org/calculator"
                   targetNamespace="http://example.org/calculator"
                   elementFormDefault="qualified"
                   attributeFormDefault="qualified">

            <xs:element name="AddValuesRequest" type="tns:AddValuesType" />
            <xs:element name="AddValuesResponse" type="tns:AddValuesResponseType" />

            <xs:complexType name="AddValuesType">
                <xs:sequence>
                    <xs:element name="FirstValue" type="xs:int" minOccurs="1" maxOccurs="1" />
                    <xs:element name="SecondValue" type="xs:int" minOccurs="1" maxOccurs="1" />
                </xs:sequence>
            </xs:complexType>

            <xs:complexType name="AddValuesResponseType">
                <xs:sequence minOccurs="1" maxOccurs="1">
                    <xs:element name="Result" type="xs:int" />
                </xs:sequence>
            </xs:complexType>

            <xs:attribute name="Timestamp" type="xs:dateTime" />
            <xs:element name="CalculationFault">
                <xs:complexType>
                    <xs:sequence>
                        <xs:element name="ErrorCode" type="xs:int" />
                        <xs:element name="Reason" type="xs:string" />
                    </xs:sequence>
                    <xs:attribute ref="tns:Timestamp" use="required" />
                </xs:complexType>
            </xs:element>

        </xs:schema>
    </wsdl:types>

    <!--
        Abstract interface
    -->

    <wsdl:interface name="CalculatorInterface">
        <wsdl:fault name="fault" element="calc:CalculationFault" />
        <wsdl:operation name="AddValues" pattern="http://www.w3.org/ns/wsdl/in-out" style="http://www.w3.org/ns/wsdl/style/iri" wsdl:safe="true">
            <wsdl:documentation>Adds up passed values and returns the result</wsdl:documentation>
            <wsdl:input messageLabel="in" element="calc:AddValuesRequest" />
            <wsdl:output messageLabel="out" element="calc:AddValuesResponse" />
            <wsdl:outfault messageLabel="fault" ref="tns:fault" />
        </wsdl:operation>
    </wsdl:interface>

    <!--
        Concrete binding definition
    -->

    <wsdl:binding name="CalculatorBinding" interface="tns:CalculatorInterface" type="http://www.w3.org/ns/wsdl/soap" soap:protocol="http://www.w3.org/2003/05/soap/bindings/HTTP/">
        <wsdl:operation ref="tns:AddValues" soap:mep="http://www.w3.org/2003/05/soap/mep/soap-response" />
        <wsdl:fault ref="tns:fault" soap:code="soap:Sender" />
    </wsdl:binding>

    <!--
        Concrete service definition
    -->

    <wsdl:service name="CalculatorService" interface="tns:CalculatorInterface">
        <wsdl:endpoint name="CalculatorEndpoint" binding="tns:CalculatorBinding" address="http://localhost:8080/services/calculator" />
    </wsdl:service>

</wsdl:description>

Unterschiede zwischen WSDL 1.1 und 2.0

Eine grafische Übersicht über die Unterschiede zwischen beiden Versionen ist in der folgenden Abbildung dargestellt.

Geben Sie hier die Bildbeschreibung ein ( Quelle )

Wie aus dem Bild ersichtlich, wurde der message entfernt, der jetzt im interface ist. Außerdem wurden einige Elemente umbenannt, andere haben eine andere Syntax, aber im Allgemeinen machen beide WSDL-Versionen im Wesentlichen dasselbe wie Version 2.0, was im Vergleich zu 1.1 etwas weniger Schreibaufwand erfordert.

Neben der geringeren Größe bei der Definition von SOAP-basierten Diensten über WSDL 2.0 bietet die neuere Version auch Funktionen zum Definieren von REST-Diensten. WSDL 2.0 oder sogar WADL werden für RESTful-Dienste NICHT empfohlen, da sie der eigentlichen Idee widersprechen.

Welchen Stil bevorzugen?

Der Abschnitt WSDL-Bindung beschreibt, wie der Dienst an das SOAP-Nachrichtenprotokoll gebunden ist. Im obigen Beispiel wurde document als Bindungsstil verwendet, der es erlaubt, den SOAP-Body wie gewünscht zu strukturieren, solange die resultierende Ausgabe eine gültige XML-Instanz ist. Dies ist der Standardbindungsstil, der häufig als Message-Oriented style .

Im Gegensatz zum document müssen RPC Anforderungskörper sowohl den Operationsnamen als auch die Menge der Methodenparameter enthalten. Die Struktur der XML-Instanz ist daher vordefiniert und kann nicht geändert werden.

Neben dem Bindungsstil definiert der Bindungsabschnitt auch ein Übersetzungsmodell für Bindungen an SOAP-Nachrichten im Namen des literal oder encoded . Der Unterschied zwischen den beiden ist, dass literal Modell hat zu einem benutzerdefinierten XSD Struktur anzupassen, die verwendet werden können , um die Anforderungen und Antworten zu bestätigen, während das encoded Modell XSD - Datentypen wie verwenden hat xs:integer oder xs:string aber im Austausch muss sich daher kein benutzerdefiniertes Schema ergeben. Dies macht es jedoch schwieriger, den Nachrichtentext zu überprüfen oder die Nachricht über XSLT in ein anderes Format umzuwandeln.

Die Kombination des Bindungsstils mit dem Use-Modell ermöglicht tatsächlich 4 verschiedene Nachrichtenergebnisse. Ein fünfter Eintrag wird der Liste hinzugefügt, der häufig verwendet wird (obwohl er nicht wirklich zum Standard gehört).

  • RPC / codiert
  • RPC / wörtliche
  • Dokument / verschlüsselt
  • Dokument / Literal
  • Dokument / Literal (verpackt)

Im Dokument- / Literalstil der Nachrichtenübertragung gibt es ein Muster, das als umschlossenes Dokument / Literal bekannt ist. Dies ist nur ein Muster und ist nicht Teil der WSDL-Spezifikation. Dieses Muster wird in JSR 224 (JAX-WS: Java-API für XML-basierte Webdienste) erwähnt. ( Quelle )

Der folgende Abschnitt enthält einen Überblick über die Unterschiede in Bezug auf die WSDL- oder Schemadeklaration und ihre Auswirkungen auf das resultierende SOAP-Nachrichtenformat beim Ändern des Bindungsstils oder der Verwendung von Modelldefinitionen.

RPC / codiert

WSDL:

...
<wsdl:message name="AddValues">
  <wsdl:part name="FirstValue" type="xsd:int" />
  <wsdl:part name="SecondValue" type="xsd:int" />
</wsdl:message>
<wsdl:message name="AddValuesResponse">
  <wsdl:part name="Result" type="xsd:int" />
</wsdl:message>

<wsdl:portType name="CalculatorEndpoint">
  <wsdl:operation="AddValues">
    <wsdl:input message="AddValues" />
    <wsdl:output message="AddValuesResponse" />
  </wsdl:operation>
</wsdl:portType>

<!-- binding style set to 'RPC' and use to 'encoded' -->
...

SOAP-Anfrage

<soap:envelope>
  <soap:body>
    <AddValues>
      <FirstValue xsi:type="xsd:int">1</FirstValue>
      <SecondValue xsi:type="xsd:int">2</SecondValue>
    </AddValues>
  </soap:body>
</soap:envelope>

SOAP-Antwort

<soap:envelope>
  <soap:body>
    <AddValuesResponse>
      <Result xsi:type="xsd:int">3</Result>
    </AddValuesResponse>
  </soap:body>
</soap:envelope>

Pros

  • unkomplizierte WSDL
  • Name des Vorgangs und Elemente, die in Anforderung und Antwort verfügbar sind

Cons

  • Explizite Deklaration von XSI-Typen
  • Schwer zu bestätigen
  • Nicht WS-I-kompatibel

RPC / wörtliche

WSDL:

...
<wsdl:message name="AddValues">
  <wsdl:part name="FirstValue" type="xsd:int" />
  <wsdl:part name="SecondValue" type="xsd:int" />
</wsdl:message>
<wsdl:message name="AddValuesResponse">
  <wsdl:part name="Result" type="xsd:int" />
</wsdl:message>

<wsdl:portType name="CalculatorEndpoint">
  <wsdl:operation="AddValues">
    <wsdl:input message="AddValues" />
    <wsdl:output message="AddValuesResponse" />
  </wsdl:operation>
</wsdl:portType>

<!-- binding style set to 'RPC' and use to 'literal' -->
...

SOAP-Anfrage

<soap:envelope>
  <soap:body>
    <AddValues>
      <FirstValue>1</FirstValue>
      <SecondValue>2</SecondValue>
    </AddValues>
  </soap:body>
</soap:envelope>

SOAP-Antwort

<soap:envelope>
  <soap:body>
    <AddValuesResult>
      <Result>3</Result>
    </AddValuesResult>
  </soap:body>
</soap:envelope>

Pros

  • unkomplizierte WSDL
  • Name des Vorgangs und Elemente, die in Anforderung und Antwort verfügbar sind
  • Keine XSI-Typspezifikation erforderlich
  • WS-I-konform

Cons

  • Schwer zu bestätigen

Dokument / verschlüsselt

Sinn macht deshalb keinen Sinn.

Dokument / Literal

WSDL:

...
<types>
  <schema>
    <element name="FirstValueElement" type="xsd:int" />
    <element name="SecondValueElement" type="xsd:int" />
    <element name="ResultValueElement" type="xsd:int" />
  </schema>
</types>

<wsdl:message name="AddValues">
  <wsdl:part name="FirstValue" element="FirstValueElement" />
  <wsdl:part name="SecondValue" element="SecondValueElement" />
</wsdl:message>
<wsdl:message name="AddValuesResponse">
  <wsdl:part name="Result" element="ResultValueElement" />
</wsdl:message>

<wsdl:portType name="CalculatorEndpoint">
  <wsdl:operation="AddValues">
    <wsdl:input message="AddValues" />
    <wsdl:output message="AddValuesResponse" />
  </wsdl:operation>
</wsdl:portType>

<!-- binding style set to 'Document' and use to 'literal' -->
...

SOAP-Anfrage

<soap:envelope>
  <soap:body>
    <FirstValueElement>1</FirstValueElement>
    <SecondValueElement>2</SecondValueElement>
  </soap:body>
</soap:envelope>

SOAP-Antwort

<soap:envelope>
  <soap:body>
    <ResultElement>3</ResultElement>
  </soap:body>
</soap:envelope>

Pros

  • Keine XSI-Typcodierung
  • Kann Körper validieren
  • WS-I entspricht den Einschränkungen

Cons

  • WSDL ist aufgrund der zusätzlichen XSD-Definition komplizierter
  • Der Operationsname geht verloren
  • WS-I lässt nur ein Kind im SOAP-Body zu

Dokument / Literal (verpackt)

WSDL:

...
<types>
  <schema>
    <element name="AddValues">
      <complexType>
        <sequence>
          <element name="FirstValue" type="xsd:int" />
          <element name="SecondValue" type="xsd:int" />
        </sequence>
      </complexType>
    </element>
    <element name="AddValuesResponse">
      <complexType>
        <sequence>
          <element name="ResultValue" type="xsd:int" />
        </sequence>
      </complexType>
    </element>
  </schema>
</types>

<wsdl:message name="AddValues">
  <wsdl:part name="in" element="AddValues" />
</wsdl:message>
<wsdl:message name="AddValuesResponse">
  <wsdl:part name="out" element="AddValuesResponse" />
</wsdl:message>

<wsdl:portType name="CalculatorEndpoint">
  <wsdl:operation="AddValues">
    <wsdl:input message="AddValues" />
    <wsdl:output message="AddValuesResponse" />
  </wsdl:operation>
</wsdl:portType>

<!-- binding style set to 'Document' and use to 'literal' -->
...

SOAP-Anfrage

<soap:envelope>
  <soap:body>
    <AddValues>
      <FirstValue>1</FirstValue>
      <SecondValue>2</SecondValue>
    </AddValues>
  </soap:body>
</soap:envelope>

SOAP-Antwort

<soap:envelope>
  <soap:body>
    <AddValuesResponse>
      <Result>3</Result>
    </AddValuesResponse>
  </soap:body>
</soap:envelope>

Pros

  • Keine XSI-Typcodierung
  • Kann Körper validieren
  • Name des Vorgangs und Elemente, die in Anforderung und Antwort verfügbar sind
  • WS-I-konform

Cons

  • WSDL ist aufgrund der zusätzlichen XSD-Definition komplizierter

UDDI

Universal Description, Discovery and Integration (UDDI) ist eine offene Brancheninitiative aus dem Jahr 2000, die als XML-basierte Yellow-Pages-Registrierung für Webservices fungiert und dabei hilft, Services zu finden, die bestimmte Aufgaben lösen. Um einen geeigneten Dienst zu finden, muss ein Dienst zuerst bei einer Web-Service-Registry wie dem UDDI registriert werden.

UDDI arbeitet mit dem SOAP-Nachrichtenaustausch und bietet Zugriff auf WSDL-Dokumente, mit denen der eigentliche Webdienst aufgerufen werden kann.

Die UDDI bietet Suchkriterien wie

  • Geschäftskennung
  • Firmenname
  • Geschäftsstandort
  • Geschäftskategorie
  • Servicetyp nach Name
  • Discovery-URLs

Ein großer Nachteil der aktuellen UDDI ist jedoch, dass nur ein einziges Kriterium innerhalb einer Suchanweisung verwendet werden kann. Bestimmte Implementierer haben daher ihre UDDI-Implementierungen modularisiert, um Abfragen zu ermöglichen, die mehrere UDDIs gleichzeitig starten, und die zurückgegebenen Ergebnisse zu aggregieren.

In der Praxis wird UDDI jedoch nicht so häufig verwendet. Einige sagen sogar, UDDI sei tot, seit IBM, Microsoft und SAP ihre UDDI-Dienste 2005 eingestellt hatten .

Weitere Hinweise:

SOAP / WSDL bieten eine breite Palette an Werkzeugunterstützung und ermöglichen auch die dynamische Erzeugung von Stub-Klassen für Clients und Server, da die Art der ausgetauschten Nachrichten und Daten durch die eingebetteten oder verknüpften XSD-Schemata genau definiert wird.

Während WSDL 2.0 weniger Aufwand für die Definition von Webdiensten hat, haben bestimmte Sprachen den neuen Standard noch nicht übernommen. Dh in Java beliebte Tools wie wsimport (von Oracle / Sun) oder wsdl2java (von Apache CXF) können WSDL 2.0-Beschreibungen nicht ordnungsgemäß verarbeiten. Aus Kompatibilitätsgründen wird daher weiterhin empfohlen, WSDL 1.1 zu verwenden. Wenn Sie einen WSDL 2.0-basierten SOAP-Dienst in Java entwickeln müssen, schauen Sie sich wsdl2java aus dem Apache Axis2- Projekt an.

Heutzutage beliebter sind jedoch entweder HTTP-basierte API-Dienste, die HTTP-Operationsaufrufe mit sauber verständlichen URIs und bestimmten Anpassungen des Protokolls kombinieren, um ihre Arbeit zu erledigen, REST- basierte Dienste, die vollständig den tatsächlichen Empfehlungen entsprechen. oder eigene Protokolle auf Byte-Ebene, wie zB OFTP2 .

SOAP ist heutzutage immer noch nützlich, wenn Sie Ihre Aufgabe nicht direkt Ressourcen zuordnen können, wie dies bei HTTP / REST-Basisdiensten der Fall ist. Die auszuführende Aufgabe stellt natürlich eine Aktion dar oder muss bestimmte Transaktionssemantiken definieren. Wenn Sie nicht über die Ressourcen zum Definieren oder Implementieren Ihres eigenen Protokolls verfügen, ist es wahrscheinlich besser, SOAP zu verwenden. SOAP ist besonders nützlich, wenn Sie sich mit Orchestrierung befassen müssen, da die WSDL-Beschreibung in Kombination mit UDDI das dynamische Kombinieren von Diensten ermöglicht.

Open-Source-Webservice für Java-Client für Wetterdienst verfügbar unter http://www.webserviceX.NET

  package com.test.ws.example;

 import javax.xml.soap.MessageFactory;
 import javax.xml.soap.MimeHeaders;
 import javax.xml.soap.SOAPBody;
 import javax.xml.soap.SOAPConnection;
 import javax.xml.soap.SOAPConnectionFactory;
 import javax.xml.soap.SOAPElement;
 import javax.xml.soap.SOAPEnvelope;
 import javax.xml.soap.SOAPMessage;
 import javax.xml.soap.SOAPPart;
 import javax.xml.transform.Source;
 import javax.xml.transform.Transformer;
 import javax.xml.transform.TransformerFactory;
 import javax.xml.transform.stream.StreamResult;

 /*
  * WSDL url :  http://www.webservicex.com/globalweather.asmx?WSDL
  * Endpoint URL: http://www.webservicex.com/globalweather.asmx   */

    public class WSClient {

   public static void main(String args[]) {

    try {
        SOAPConnectionFactory soapConnectionFactory = SOAPConnectionFactory.newInstance();
        SOAPConnection soapConnection = soapConnectionFactory.createConnection();

        // Generate SOAP request XML

        MessageFactory messageFactory = MessageFactory.newInstance();
        SOAPMessage soapMessage = messageFactory.createMessage();
        MimeHeaders header = soapMessage.getMimeHeaders();
        header.setHeader("SOAPAction", "http://www.webserviceX.NET/GetCitiesByCountry");
        SOAPPart soapPart = soapMessage.getSOAPPart();
        SOAPEnvelope envelope = soapPart.getEnvelope();
        envelope.addNamespaceDeclaration("web", "http://www.webserviceX.NET");
        SOAPBody soapBody = envelope.getBody();
        SOAPElement soapBodyElem = soapBody.addChildElement("GetCitiesByCountry", "web");
        SOAPElement soapBodyElem1 = soapBodyElem.addChildElement("CountryName", "web");
        soapBodyElem1.addTextNode("INDIA");
        soapMessage.saveChanges();
        soapMessage.writeTo(System.out);
        
                    
        // Call webservice endpint
        String url = "http://www.webservicex.com/globalweather.asmx";
        SOAPMessage soapResponse = soapConnection.call(soapMessage, url);
        Source sourceContent = soapResponse.getSOAPPart().getContent();

        // Print SOAP response
        TransformerFactory transformerFactory = TransformerFactory.newInstance();
        Transformer transformer = transformerFactory.newTransformer();
        System.out.println("Response SOAP Message \n");
        StreamResult result = new StreamResult(System.out);
        transformer.transform(sourceContent, result);
        soapConnection.close();

    } catch (Exception e) {

        e.printStackTrace();
    }
}

}

Erstellen eines einfachen Web-Service und Clients mit JAX-WS (Dokument / Literal)

Dies ist das Projektverzeichnis.

Projektverzeichnis

  1. Eine Service-Endpunkt-Schnittstelle

Zuerst erstellen wir eine Service-Endpunkt-Schnittstelle. Die Annotation javax.jws.WebService @WebService definiert die Klasse als Web-Service-Endpunkt.


import javax.jws.WebMethod;
import javax.jws.WebService;
import javax.jws.soap.SOAPBinding;
import javax.jws.soap.SOAPBinding.Style;
import javax.jws.soap.SOAPBinding.Use;

// Service Interface with customize targetNamespace
@WebService(targetNamespace = "http://hello-soap/ws")
@SOAPBinding(style = Style.DOCUMENT, use=Use.LITERAL) //optional
public interface HelloSoap {

    @WebMethod String getHelloSoap(String name);

}

  1. Service Endpoint-Implementierung (SEI)

Als Nächstes erstellen wir eine Service-Endpunkt-Implementierung. Wir werden eine explizite Schnittstelle durch Hinzufügen des erstellen endpointInterface Element zum @WebService Anmerkung in der Implementierungsklasse. Hier einige Regeln 28.1.1 Anforderungen an einen JAX-WS-Endpunkt , an die sich JAX-WS-Endpunkte halten müssen. Die getHelloSoap-Methode gibt eine Begrüßung mit dem übergebenen Namen an den Client zurück.


import javax.jws.WebService;

// Customized Service Implementation (portName,serviceName,targetNamespace are optional)

@WebService(portName = "HelloSoapPort", serviceName = "HelloSoapService",
endpointInterface = "com.wonderland.hellosoap.HelloSoap", targetNamespace = "http://hello-soap/ws")
public class HelloSoapImpl implements HelloSoap {

    @Override
    public String getHelloSoap(String name) {
        return "[JAX-WS] Hello : " + name;
    }

}

  1. Herausgeber des Web-Service-Endpunkts

import javax.xml.ws.Endpoint;

public class HelloSoapPublisher {

    public static void main(String[] args) {
        // creating web service endpoint publisher
        Endpoint.publish("http://localhost:9000/ws/hello-soap", new HelloSoapImpl());
    }

}

  1. Als nächstes führen wir HelloSoapPublisher.java als Java-Anwendung aus. Anschließend können Sie die WSDL-Datei http://localhost:9000/ws/hello-soap?wsdl in einem Webbrowser die URL http://localhost:9000/ws/hello-soap?wsdl .
http: // localhost: 9000 / ws / hallo-soap? wsdl

Wenn das XML-Datenformat im Webbrowser angezeigt wird, können Sie mit dem nächsten Schritt fortfahren.

Hallo Seife? Wsdl

Hinweis:
Wenn Sie eine Fehlermeldung erhalten, müssen Sie möglicherweise das wsgen Tool verwenden, um die erforderlichen tragbaren JAX-WS-Artefakte zu generieren. Wir sind hier nicht über das wsgen Tool wsgen .

  1. Web Service Client

Abschließend erstellen wir einen Client, der auf unseren veröffentlichten Service zugreift.


import java.net.URL;

import javax.xml.namespace.QName;
import javax.xml.ws.Service;

public class HelloSoapClient {

    public static void main(String[] args) throws Exception {

        // create wsdl url
        URL wsdlDocumentUrl = new URL("http://localhost:8000/ws/hello-soap?wsdl");
        QName helloSoapService = new QName("http://hello-soap/ws", "HelloSoapService");
        // create web service
        Service service = Service.create(wsdlDocumentUrl, helloSoapService);
        // get object of pointed service port
        HelloSoap helloSoap = service.getPort(HelloSoap.class);
        // testing request
        System.out.println(helloSoap.getHelloSoap("Soap "));

    }

}

Ausgabe: [JAX-WS] Hello : Soap

Hinweis: Die 8000 in unserem Webservice-Client auf 8000 geändert. Der Grund hier ist, ich habe Eclipse IDE verwendet, ein eingebautes TCP/IP monitor Tool, um Nachrichten zu verfolgen . Für Funktionstests versuchen Sie es mit SoapUI | Funktionstest für SOAP- und REST-APIs .



Modified text is an extract of the original Stack Overflow Documentation
Lizenziert unter CC BY-SA 3.0
Nicht angeschlossen an Stack Overflow