我正在服务器端使用JAX-WS完成Web服务的工作。在许多域对象中,我使用@XmlRootElement
来帮助促进使用JAXB将XML文件解组到服务中。一切顺利,输出就是我期望看到的使用SoapUI。
但是,当我使用wsimport创建客户端时(作为其他开发人员的便利DAO),我开始在客户端集成测试类中遇到NullPointerExceptions。
对webservice的调用工作正常,客户端收到响应,但我的更复杂的对象为null。简单的属性,如字符串,返回了大量可用数据,但不是更大的对象。
通过使用简单的字符串重新创建服务并迁移到更复杂的对象的迭代,我发现当客户端收到使用@XmlRootElement
在服务器上声明的对象时,这些是null的对象。如果服务器对象没有@XmlRootElement
注释,则客户端会收到所有复杂荣耀中的所有数据。
最初缺少@XmlRootElement
让我适合解组服务器上的数据,但this answer帮助了我。
因此,由于@XmlRootElement
注释(在服务器上!),wsimport客户端在解组Web服务响应时无声地失败的现象让我担心。在这种情况下,我控制了双方并且可以做些什么。但是,如果我无法控制服务器怎么办?我如何仅使用wsimport生成的代码解决这个问题?
答案 0 :(得分:1)
找到答案或原因,以为我会分享。
@XmlRootElement
注释对于普通JAXB
绑定很有用,但是当对象(以及生成的XML)打包为SOAP
响应时,它们可能并不完全相同匹配WSDL
的数据表示,具体取决于其他注释的值。
使用@XmlRootElement
方法返回的服务器上的类@WebMethod
注释,WSDL
将包含元素定义,例如:
<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的有效性方面存在某种程度的懒惰。我们吸取的教训是,在name
和targetNamespace
上使用@WebResult
注释来描述您的网络服务方法。 @XmlRootElement
注释需要与name
中的targetNamespace
匹配。当它们全部匹配时,解组按预期发生。当这些值不匹配时,由wsimport
生成和注释的存根类将无法正确使用XML。