簡體   English   中英

Apache CXF在Web服務上的命名空間問題

[英]namespace issue on web service with Apache CXF

我正在使用Apache CXF 2.7.3,並遇到一個我真的不明白的命名空間問題。 我已經嘗試過廣泛搜索,但我找到的大部分結果都是針對不同的行為。 問題是在調用Web服務時,如果參數元素是名稱空間限定的,它將失敗。 消息中的所有其他元素都是合格的,它接受它,而不是參數元素。 這是精確的行為:

請求WITHOUT參數元素限定:

<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" 
                  xmlns:ord="http://www.example.org/order">
<soapenv:Header/>
   <soapenv:Body>
      <ord:getOrder>
         <id>a</id>
      </ord:getOrder>
   </soapenv:Body>
</soapenv:Envelope>

結果成功:

<soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
   <soap:Body>
      <ns2:getOrderResponse xmlns:ns2="http://www.example.org/order">
         <return>
            <ns2:errorCode/>
            <ns2:errorMessage/>
            <ns2:order>
               <ns2:orderNumber>ABC123</ns2:orderNumber>
               <ns2:lastName>Smith</ns2:lastName>
            </ns2:order>
         </return>
      </ns2:getOrderResponse>
   </soap:Body>
</soap:Envelope>

請求WITH參數限定:

<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" 
                  xmlns:ord="http://www.example.org/order">
   <soapenv:Header/>
   <soapenv:Body>
      <ord:getOrder>
         <ord:id>a</ord:id>
      </ord:getOrder>
   </soapenv:Body>
</soapenv:Envelope>

導致JAXB異常:

<soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
   <soap:Body>
      <soap:Fault>
         <faultcode>soap:Client</faultcode>
         <faultstring>Unmarshalling Error: unexpected element (uri:"http://www.example.org/order", local:"id"). Expected elements are &lt;{}id></faultstring>
      </soap:Fault>
   </soap:Body>
</soap:Envelope>

在我所做的所有研究中,這通常意味着命名空間在某處不匹配。 但是我已經徹底檢查了它,並且命名空間在任何地方都是相同的,包括ObjectFactory.class,package-info.class和cxf-servlet.xml配置文件以及@WebService注釋。 任何人都可以指出我正確的方向,我在這里失蹤了什么?

問題的根源是wsgen,我認為這是一個錯誤。 它不會使wsdl和jaxb生成的類兼容。 在jaxb生成的類中,元素不是默認形式限定的,它將參數元素放入空命名空間。 但是在WSDL中,它默認的表單限定,其中存在問題。 可能有很多方法可以解決這個問題,我發現最快速和最臟的方法是在@WebParam注釋上設置targetNamespace。 以下是用於演示我的意思的代碼片段,我希望這可以幫助遇到此問題的其他人。

以下是我最初為自下而上的實現類所做的事情:

@WebService(serviceName="OrderService")
public class OrderService {

    public OrderResponse getOrder(@WebParam(name="id", targetNamespace="http://www.example.org/order") String id)  {

這將導致以下生成的JAXB類。 正如您所看到的那樣,它為root設置了命名空間,但它不是形式限定的,並且它也不生成package-info文件。

@XmlRootElement(name = "getOrder", namespace = "http://www.example.org/order")
@XmlAccessorType(XmlAccessType.FIELD)
@XmlType(name = "getOrder", namespace = "http://www.example.org/order")

public class GetOrder {

    @XmlElement(name = "id")
    private java.lang.String id;

然后我更改了服務實現類,將命名空間添加到@WebParam:

@WebService(serviceName="OrderService", targetNamespace="http://www.example.org/order")
public class OrderService {

    public OrderResponse getOrder(@WebParam(name="id", targetNamespace="http://www.example.org/order") String id)  {

雖然這不會使默認表單限定,但它會將命名空間添加到生成的JAXB類中的元素:

@XmlRootElement(name = "getOrder", namespace = "http://www.example.org/order")
@XmlAccessorType(XmlAccessType.FIELD)
@XmlType(name = "getOrder", namespace = "http://www.example.org/order")

public class GetOrder {

    @XmlElement(name = "id", namespace = "http://www.example.org/order")
    private java.lang.String id;

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM