我想在 CXF codegen 上添加 @XmlRoot 注释
I would like to add @XmlRoot annotation on CXF codegen
我有一个包含以下条目的 WSDL 文件:
<?xml version="1.0" encoding="UTF-8"?>
<wsdl:definitions targetNamespace="urn:CP_Ablakido" xmlns:s0="urn:CP_Ablakido" xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/" xmlns:soapenc="http://schemas.xmlsoap.org/soap/encoding/" xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
<wsdl:types>
<xsd:schema elementFormDefault="qualified" targetNamespace="urn:CP_Ablakido">
<xsd:element name="GetList_11" type="s0:InputMapping1"/>
<xsd:complexType name="InputMapping1">
<xsd:sequence>
<xsd:element name="Qualification" type="xsd:string"/>
<xsd:element name="startRecord" type="xsd:string"/>
<xsd:element name="maxLimit" type="xsd:string"/>
</xsd:sequence>
</xsd:complexType>
<xsd:element name="GetList_11Response" type="s0:OutputMapping1"/>
<xsd:complexType name="OutputMapping1">
<xsd:sequence>
<xsd:element maxOccurs="unbounded" name="getListValues">
<xsd:complexType>....
我使用具有以下设置的 CXF Codegen 插件:
<plugin>
<groupId>org.apache.cxf</groupId>
<artifactId>cxf-codegen-plugin</artifactId>
<executions>
<execution>
<id>generate-sources</id>
<phase>generate-sources</phase>
<configuration>
<sourceRoot>${basedir}/target/generated-sources/wsdl2java</sourceRoot>
<encoding>UTF-8</encoding>
</configuration>
<goals>
<goal>wsdl2java</goal>
</goals>
</execution>
</executions>
</plugin>
生成的 java 代码如下所示:
@XmlAccessorType(XmlAccessType.FIELD)
@XmlType(name = "OutputMapping1", propOrder = {
"getListValues"
})
public class OutputMapping1 {
@XmlElement(required = true)
protected List<OutputMapping1 .GetListValues> getListValues;
问题是这里缺少@XmlRootElement。还有另一个类似的问题
- maven-cxf-codegen-plugin using Jaxb binding to add inheritance for all generated classes
- Annotating CXF (wsdl2java) generated package
- externally create jaxb annotations for class
正如其他答案提到的,我可以放置绑定文件。
所以我创建了一个包含以下内容的绑定文件:
<jaxb:bindings
xmlns:jaxb="http://java.sun.com/xml/ns/jaxb"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
xmlns:xjc="http://java.sun.com/xml/ns/jaxb/xjc"
xmlns:annox="http://annox.dev.java.net"
version="2.0">
<jaxb:bindings node="//xsd:element[@name='GetList_11Response']">
<annox:annotate target="class">
<annox:annotate annox:class="javax.xml.bind.annotation.XmlRootElement" name="GetList_11Response"/>
</annox:annotate>
</jaxb:bindings>
</jaxb:bindings>
并且我已将以下块添加到 POM.XML:
<wsdlOptions>
<wsdlOption>
<wsdl>${basedir}/src/main/resources/wsdl/CP_Ablakido_1.wsdl</wsdl>
<bindingFiles>
<bindingFile>${basedir}/src/main/resources/wsdl/CP_Ablakido_1.xjb
</bindingFile>
</bindingFiles>
</wsdlOption>
</wsdlOptions>
之后我收到错误消息:
com.sun.istack.SAXParseException2; systemId: file:/Project/icp-integration/icpiCameI/src/main/resources/wsdl/CP_Ablakido_1.xjb; lineNumber: 9; columnNumber: 72; XPath evaluation of "//xs:element[@name='GetList_11Response']" results in empty target node
at com.sun.tools.xjc.reader.internalizer.Internalizer.reportError(Internalizer.java:624)
at com.sun.tools.xjc.reader.internalizer.Internalizer.reportError(Internalizer.java:618)
at com.sun.tools.xjc.reader.internalizer.Internalizer.buildTargetNodeMap(Internalizer.java:294)
at com.sun.tools.xjc.reader.internalizer.Internalizer.buildTargetNodeMap(Internalizer.java:390)
at com.sun.tools.xjc.reader.internalizer.Internalizer.transform(Internalizer.java:146)
所以我不知道如何准确描述当 complexType 为 OutputMapping1 时,然后将 @XmlRootElement 放入 OutputMapping1.java 中,名称为 "GetList_11Response"。
我找到了解决方案。这很棘手,因为:
- 必须处理 XSD 内嵌在 WSDL 中的问题。 (诀窍是 schemaLocation="CP_Ablakido_1.wsdl#types1"。它告诉 JAXB 在 WSDL 文件中使用节点。)
- 必须配置 CXF 才能使用 XJC 插件(annox)。
必须将以下片段添加到 POM.XML:
<wsdlOption>
<wsdl>${basedir}/src/main/resources/wsdl/CP_Ablakido_1.wsdl</wsdl>
<bindingFiles>
<bindingFile>${basedir}/src/main/resources/wsdl/CP_Ablakido_1.xjb</bindingFile>
</bindingFiles>
<extraargs><extraarg>-xjc-Xannotate</extraarg></extraargs>
</wsdlOption>
依赖项必须添加到插件中:
<dependency>
<groupId>org.jvnet.jaxb2_commons</groupId>
<artifactId>jaxb2-basics-annotate</artifactId>
<version>0.6.0</version>
</dependency>
<dependency>
<groupId>org.apache.cxf.xjcplugins</groupId>
<artifactId>cxf-xjc-ts</artifactId>
<version>3.0.5</version>
</dependency>
XJB 文件:
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<jaxb:bindings version="2.0"
xmlns:jaxb="http://java.sun.com/xml/ns/jaxb"
jaxb:extensionBindingPrefixes="annox xjc"
xmlns:xjc="http://java.sun.com/xml/ns/jaxb/xjc"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
xmlns:annox="http://annox.dev.java.net"
xmlns:inheritance="http://jaxb2-commons.dev.java.net/basic/inheritance">
<jaxb:bindings schemaLocation="CP_Ablakido_1.wsdl#types1" node="/xs:schema">
<jaxb:bindings node="//xs:complexType[@name='InputMapping1']">
<annox:annotate target="class">
<annox:annotate annox:class="javax.xml.bind.annotation.XmlRootElement" name="GetList_11"/>
</annox:annotate>
</jaxb:bindings>
<jaxb:bindings node="//xs:complexType[@name='OutputMapping1']">
<annox:annotate target="class">
<annox:annotate annox:class="javax.xml.bind.annotation.XmlRootElement" name="GetList_11Response"/>
</annox:annotate>
</jaxb:bindings>
</jaxb:bindings>
</jaxb:bindings>
@du-it 据我了解,您不想将 XmlRootElement 自动应用于所有 类。
这是原因:
https://community.oracle.com/blogs/kohsuke/2006/03/03/why-does-jaxb-put-xmlrootelement-sometimes-not-always
因此,对每种类型分别进行处理才是正确的做法。
我有一个包含以下条目的 WSDL 文件:
<?xml version="1.0" encoding="UTF-8"?>
<wsdl:definitions targetNamespace="urn:CP_Ablakido" xmlns:s0="urn:CP_Ablakido" xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/" xmlns:soapenc="http://schemas.xmlsoap.org/soap/encoding/" xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
<wsdl:types>
<xsd:schema elementFormDefault="qualified" targetNamespace="urn:CP_Ablakido">
<xsd:element name="GetList_11" type="s0:InputMapping1"/>
<xsd:complexType name="InputMapping1">
<xsd:sequence>
<xsd:element name="Qualification" type="xsd:string"/>
<xsd:element name="startRecord" type="xsd:string"/>
<xsd:element name="maxLimit" type="xsd:string"/>
</xsd:sequence>
</xsd:complexType>
<xsd:element name="GetList_11Response" type="s0:OutputMapping1"/>
<xsd:complexType name="OutputMapping1">
<xsd:sequence>
<xsd:element maxOccurs="unbounded" name="getListValues">
<xsd:complexType>....
我使用具有以下设置的 CXF Codegen 插件:
<plugin>
<groupId>org.apache.cxf</groupId>
<artifactId>cxf-codegen-plugin</artifactId>
<executions>
<execution>
<id>generate-sources</id>
<phase>generate-sources</phase>
<configuration>
<sourceRoot>${basedir}/target/generated-sources/wsdl2java</sourceRoot>
<encoding>UTF-8</encoding>
</configuration>
<goals>
<goal>wsdl2java</goal>
</goals>
</execution>
</executions>
</plugin>
生成的 java 代码如下所示:
@XmlAccessorType(XmlAccessType.FIELD)
@XmlType(name = "OutputMapping1", propOrder = {
"getListValues"
})
public class OutputMapping1 {
@XmlElement(required = true)
protected List<OutputMapping1 .GetListValues> getListValues;
问题是这里缺少@XmlRootElement。还有另一个类似的问题
- maven-cxf-codegen-plugin using Jaxb binding to add inheritance for all generated classes
- Annotating CXF (wsdl2java) generated package
- externally create jaxb annotations for class
正如其他答案提到的,我可以放置绑定文件。 所以我创建了一个包含以下内容的绑定文件:
<jaxb:bindings
xmlns:jaxb="http://java.sun.com/xml/ns/jaxb"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
xmlns:xjc="http://java.sun.com/xml/ns/jaxb/xjc"
xmlns:annox="http://annox.dev.java.net"
version="2.0">
<jaxb:bindings node="//xsd:element[@name='GetList_11Response']">
<annox:annotate target="class">
<annox:annotate annox:class="javax.xml.bind.annotation.XmlRootElement" name="GetList_11Response"/>
</annox:annotate>
</jaxb:bindings>
</jaxb:bindings>
并且我已将以下块添加到 POM.XML:
<wsdlOptions>
<wsdlOption>
<wsdl>${basedir}/src/main/resources/wsdl/CP_Ablakido_1.wsdl</wsdl>
<bindingFiles>
<bindingFile>${basedir}/src/main/resources/wsdl/CP_Ablakido_1.xjb
</bindingFile>
</bindingFiles>
</wsdlOption>
</wsdlOptions>
之后我收到错误消息:
com.sun.istack.SAXParseException2; systemId: file:/Project/icp-integration/icpiCameI/src/main/resources/wsdl/CP_Ablakido_1.xjb; lineNumber: 9; columnNumber: 72; XPath evaluation of "//xs:element[@name='GetList_11Response']" results in empty target node
at com.sun.tools.xjc.reader.internalizer.Internalizer.reportError(Internalizer.java:624)
at com.sun.tools.xjc.reader.internalizer.Internalizer.reportError(Internalizer.java:618)
at com.sun.tools.xjc.reader.internalizer.Internalizer.buildTargetNodeMap(Internalizer.java:294)
at com.sun.tools.xjc.reader.internalizer.Internalizer.buildTargetNodeMap(Internalizer.java:390)
at com.sun.tools.xjc.reader.internalizer.Internalizer.transform(Internalizer.java:146)
所以我不知道如何准确描述当 complexType 为 OutputMapping1 时,然后将 @XmlRootElement 放入 OutputMapping1.java 中,名称为 "GetList_11Response"。
我找到了解决方案。这很棘手,因为:
- 必须处理 XSD 内嵌在 WSDL 中的问题。 (诀窍是 schemaLocation="CP_Ablakido_1.wsdl#types1"。它告诉 JAXB 在 WSDL 文件中使用节点。)
- 必须配置 CXF 才能使用 XJC 插件(annox)。
必须将以下片段添加到 POM.XML:
<wsdlOption>
<wsdl>${basedir}/src/main/resources/wsdl/CP_Ablakido_1.wsdl</wsdl>
<bindingFiles>
<bindingFile>${basedir}/src/main/resources/wsdl/CP_Ablakido_1.xjb</bindingFile>
</bindingFiles>
<extraargs><extraarg>-xjc-Xannotate</extraarg></extraargs>
</wsdlOption>
依赖项必须添加到插件中:
<dependency>
<groupId>org.jvnet.jaxb2_commons</groupId>
<artifactId>jaxb2-basics-annotate</artifactId>
<version>0.6.0</version>
</dependency>
<dependency>
<groupId>org.apache.cxf.xjcplugins</groupId>
<artifactId>cxf-xjc-ts</artifactId>
<version>3.0.5</version>
</dependency>
XJB 文件:
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<jaxb:bindings version="2.0"
xmlns:jaxb="http://java.sun.com/xml/ns/jaxb"
jaxb:extensionBindingPrefixes="annox xjc"
xmlns:xjc="http://java.sun.com/xml/ns/jaxb/xjc"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
xmlns:annox="http://annox.dev.java.net"
xmlns:inheritance="http://jaxb2-commons.dev.java.net/basic/inheritance">
<jaxb:bindings schemaLocation="CP_Ablakido_1.wsdl#types1" node="/xs:schema">
<jaxb:bindings node="//xs:complexType[@name='InputMapping1']">
<annox:annotate target="class">
<annox:annotate annox:class="javax.xml.bind.annotation.XmlRootElement" name="GetList_11"/>
</annox:annotate>
</jaxb:bindings>
<jaxb:bindings node="//xs:complexType[@name='OutputMapping1']">
<annox:annotate target="class">
<annox:annotate annox:class="javax.xml.bind.annotation.XmlRootElement" name="GetList_11Response"/>
</annox:annotate>
</jaxb:bindings>
</jaxb:bindings>
</jaxb:bindings>
@du-it 据我了解,您不想将 XmlRootElement 自动应用于所有 类。 这是原因: https://community.oracle.com/blogs/kohsuke/2006/03/03/why-does-jaxb-put-xmlrootelement-sometimes-not-always 因此,对每种类型分别进行处理才是正确的做法。