jaxb2 从主 xsd 生成的类和通用 xsd 具有不同的命名空间

问题描述 投票:0回答:1

我有 2 个 xsd 模式,我使用 maven-jaxb2-plugin 从中生成一个类消息。主要的 xsd 是 message.xsd,它导入 common.xsd,其中包含一些常见类型。然而两者都有不同的目标命名空间。

这会导致 jaxb xml unmarshaller 无法读取 xml 中的字段并使用默认值。如果在生成的类中我手动将命名空间设置为“消息”,它就可以工作。有没有办法将两个生成的类字段放置在同一名称空间下?或者我的 XML 消息可能是错误的?或者我是否在某处缺少 jaxb2 生成器参数?我应该使用 jaxb 绑定来解决这个问题吗?

我无法更改 xsd 命名空间定义。很多答案都非常接近我需要的,但没有一个是我遇到的实际问题。

这会生成一个看起来像这样的 Message 类:

@XmlAccessorType(XmlAccessType.FIELD)
@XmlType(name = "", propOrder = {
    "computer"
})
@XmlRootElement(name = "message", namespace = "message")
public class Message implements ToString2
{
    @XmlAccessorType(XmlAccessType.FIELD)
    @XmlType(name = "", propOrder = {
        "date",
        "info"
    })
    public static class Computer implements ToString2
    {
    @XmlElement(namespace = "message", required = true)
        protected int date;
        @XmlElement(name = "info", namespace = "message", required = true)
        protected InfoType info;
    }
}

Info 类是从 common.xsd 生成的,它看起来像这样:

@XmlAccessorType(XmlAccessType.FIELD)
@XmlType(name = "InfoType", propOrder = {
    "number",
    "id"
})
public class InfoType implements ToString2
{

    @XmlElement(namespace = "")
    @XmlSchemaType(name = "integer")
    protected int number;
    @XmlElement(namespace = "")
    @XmlSchemaType(name = "integer")
    protected int id;
}

我发送此 xml:

<?xml version="1.0" encoding="utf-8"?>
<message xmlns="message">
    <computer>
        <info>
            <name>2</name>
            <id>999998</id>
        </info>
        <date>20220508</date>
    </computer>
</message>

package-info.java 将命名空间设置为“common”,这就是为什么我假设 Info 中字段的命名空间是“”,它看起来像这样:

@javax.xml.bind.annotation.XmlSchema(namespace = "common", elementFormDefault = javax.xml.bind.annotation.XmlNsForm.QUALIFIED)
package com.myapp.message

pom:

<plugin>
    <groupId>org.jvnet.jaxb2.maven2</groupId>
    <artifactId>maven-jaxb2-plugin</artifactId>
    <version>0.14.0</version>
    <dependencies>
        <dependency>
            <groupId>org.glassfish.jaxb</groupId>
            <artifactId>jaxb-runtime</artifactId>
            <version>2.3.3</version>
        </dependency>
    </dependencies>
    <configuration>
        <accessExternalSchema>all</accessExternalSchema>
        <specVersion>2.1</specVersion>
        <cleanPackageDirectories>false</cleanPackageDirectories>
        <extension>true</extension>
        <args>
            <arg>-Xfluent-api</arg>
            <arg>-XtoString</arg>
        </args>
        <plugins>
            <plugin>
                <groupId>net.java.dev.jaxb2-commons</groupId>
                <artifactId>jaxb-fluent-api</artifactId>
                <version>${maven-jaxb2-plugin.fluent-api.version}</version>
            </plugin>
            <plugin>
                <groupId>org.jvnet.jaxb2_commons</groupId>
                <artifactId>jaxb2-basics</artifactId>
                <version>${jaxb2-basics-runtime.version}</version>
            </plugin>
        </plugins>
    </configuration>
    <executions>
        <execution>
            <id>generate-message</id>
            <phase>generate-sources</phase>
            <goals>
                <goal>generate</goal>
            </goals>
            <configuration>
                <schemaDirectory>src/main/resources/message</schemaDirectory>
                <schemaIncludes>
                    <include>message.xsd</include>
                </schemaIncludes>
                <bindingDirectory>src/main/resources/jaxb</bindingDirectory>
                <generateDirectory>target/generated-sources/jaxb/message</generateDirectory>
                <generatePackage>com.myapp.message
                </generatePackage>
            </configuration>
        </execution>
    </executions>
</plugin>

从其他 xsd 代中,我假设将 targetNamespace 更改为相同的命名空间并使用 include 而不是 import 可以解决问题,但这不是一个选项。

手动更改 @XmlElement(namespace = "") 中的命名空间解决了问题,但这对我来说没有多大作用,因为它会在下一代被重写。

我尝试调查xjb。但是我不确定这是否真的是这样,如果我将其设置为绑定到顶部元素,它在解析 commons.xsd 中的类型时会遇到麻烦 - 可能值得追求?

spring-boot xsd jaxb code-generation maven-jaxb2-plugin
1个回答
0
投票

我们没有

common.xsd
一代,但我认为您不应该将公共内容和消息生成到同一个包中(标签
generatePackage
)。

通过这样做,Jaxb 不知道哪个包注释是正确的。

您还可以按照升级指南

升级到至少v2版本的maven-jaxb2-plugin
© www.soinside.com 2019 - 2024. All rights reserved.