2

サーバー側でJAX-WSを使用してWebサービスの作業を完了していました。私が使用したドメインオブジェクトの多くでは、@XmlRootElementJAXBを使用してXMLファイルをサービスにアンマーシャリングするのを容易にしました。すべてうまくいき、出力はSoapUIを使用して期待したものでした。

ただし、wsimportを使用してクライアントを作成したとき(他の開発者にとって便利なDAOとして)、クライアント統合テストクラスでNullPointerExceptionsが発生し始めました。

Webサービスへの呼び出しは正しく機能し、クライアントは応答を受信しましたが、より複雑なオブジェクトはnullでした。文字列のような単純な属性は、使用可能なデータでいっぱいを返していましたが、より大きなオブジェクトは返していませんでした。

単純な文字列を使用してサービスを再作成し、より複雑なオブジェクトに移行することを繰り返した結果、クライアントがサーバーで宣言されたオブジェクトを受け取ったときに@XmlRootElement、これらがnullのオブジェクトであることがわかりました。サーバーオブジェクトに注釈がない場合@XmlRootElement、クライアントはその複雑な栄光のすべてですべてのデータを受信しました。

当初、この欠如は@XmlRootElementサーバー上のデータのマーシャリングを解除することに適合しましたが、この回答は私を助けてくれました。

@XmlRootElementそのため、 (サーバー上の!)アノテーションが原因で、wsimportクライアントがWebサービス応答のアンマーシャリングにサイレントに失敗するという現象が懸念されます。この場合、私は両方の側を制御し、それについて何かをすることができました。しかし、サーバーを制御できない場合はどうなりますか?wsimportで生成されたコードだけでこれをどのように解決できますか?

4

1 に答える 1

2

答え、または理由を見つけたので、私が共有しようと思いました。

@XmlRootElementアノテーションはプレーンJAXBバインディングに役立ちますが、オブジェクト(および結果のXML)が応答としてパッケージ化されている場合、他のアノテーションの値によっては、データの表現とSOAP正確に一致しない可能性があります。WSDL

メソッド@XmlRootElementによって返されるサーバー上のクラスのアノテーションを使用すると、次のような要素定義が含まれます。@WebMethodWSDL

<xs:element name="foo" type="tns:FooType"/>

次に、他の場所で、WSDL次のようなシーケンスに要素への参照を含めます。

<xs:seqeunce>
<xs:element maxOccurs="unbounded" minOccurs="0" ref="tns:foo"/>
</xs:sequence>

この参照は、アノテーションによって引き起こされ@XmlRootElement、SOAP応答の実際のXMLと比較してルート要素宣言の意図を混乱させる可能性があります。

対照的に、サーバーオブジェクトWSDLに注釈なしで生成されたものには、宣言@XmlRootElementがまったく含まれていません。<xs:element name="foo"/>むしろ、その要素は次のように記述されます。

<xs:sequence>
<xs:element maxOccurs="unbounded" minOccurs="0" name="foo" type="tns:FooType"/>
</xs:sequence>

これはおそらく、SOAP応答XMLの表現方法とよりよく一致し、によって生成されたクラスへのXMLのアンマーシャリングはwsimport問題なく機能します。

@XmlRootElementサービスでの使用方法はJAX-WS

wsimportサービスによって返されるXMLの有効性においてある程度の怠惰を処理しているようです。学んだ教訓は、Webサービスメソッドを説明する注釈の使用nameと注釈に熱心に取り組むことです。アノテーションは内で一致する必要があります。それらがすべて一致すると、アンマーシャリングは期待どおりに行われます。これらの値が一致しない場合、によって生成および注釈が付けられたスタブクラスはXMLを適切に使用できません。targetNamespace@WebResult@XmlRootElementnametargetNamespacewsimport

于 2013-05-08T15:58:18.197 に答える