【问题标题】:Is there a way to deal with duplicate element definitions across multiple .xsd files in JAXB?有没有办法处理 JAXB 中多个 .xsd 文件中的重复元素定义?
【发布时间】:2022-01-17 14:17:21
【问题描述】:

我有几十个 .xsd 文件要为其自动生成代码。当我尝试同时生成所有文件时,其中一些文件的名称会发生​​冲突。

我只专注于尝试让其中 2 个发挥作用。

当我得到这 2 个工作时,我会解决其余的问题。但我现在只关注其中两个文件。我无法控制它们,它们来自供应商并遵循“标准”,因此出于多种原因编辑它们不是一种选择

我正在使用maven-jaxb2-plugin 来处理这些文件。

我添加了一个binding.xjb 文件,正如mat b 的答案和我在网上找到的其他说明中的链接中所建议的那样。但是我收到以下错误,没有输出。

<?xml version="1.0" encoding="UTF-8"?>
<jxb:bindings version="2.1"
              xmlns:xsi="http://www.w3.org/2000/10/XMLSchema-instance"
              xmlns:xjc="http://java.sun.com/xml/ns/jaxb/xjc"
              xmlns:jxb="http://java.sun.com/xml/ns/jaxb"
              xmlns:xs="http://www.w3.org/2001/XMLSchema"
              xsi:schemaLocation=" http://java.sun.com/xml/ns/jaxb http://java.sun.com/xml/ns/jaxb/bindingschema_2_0.xsd">
  <jxb:bindings schemaLocation="mac-3.4.xsd">
    <jxb:schemaBindings>
      <jxb:package name="my.company.mac"/>
    </jxb:schemaBindings>
  </jxb:bindings>
  <jxb:bindings schemaLocation="mac-stylesheet-3.4.xsd">
    <jxb:schemaBindings>
      <jxb:package name="my.company.stylesheet"/>
    </jxb:schemaBindings>
  </jxb:bindings>
</jxb:bindings>

出现以下错误

[ERROR] Error while parsing schema(s).Location [ file:/C:/Users/Jarrod%20Roberson/Projects/spa-tools/spa-lib/src/main/sc
hema/mac-stylesheet-3.4.xsd{165,33}].
org.xml.sax.SAXParseException: 'halign' is already defined

有问题的元素是:(还有很多其他的,这只是第一个冲突的)

<xsd:simpleType name="halign">
  <xsd:restriction base="xsd:string">
    <xsd:enumeration value="left" />
    <xsd:enumeration value="center" />
    <xsd:enumeration value="right" />
  </xsd:restriction>
</xsd:simpleType>

并且在每个.xsd 文件中都是相同的,我该如何解决这种重复,要么只生成一个类,要么将每个类都生成到它们自己的包命名空间中?

这不是唯一一个像这样的重复元素,它们有很多,所以仅仅尝试从文件中删除它们也不是一种选择。

这个halign 位于多个.xsd 文件中,我想将它们放在各自的包中,或者能够告诉编译器使用生成的第一个包。

这是我在尝试外部.xjb 文件之前开始的地方,只需在pom.xml 中指定package

如何配置绑定以忽略重复配置、将它们映射到单独的包或将它们映射到现有实现?

【问题讨论】:

    标签: java maven jaxb maven-plugin maven-jaxb2-plugin


    【解决方案1】:

    我对此有一个中途的解决方案,但它非常耗时。 我必须为每个具有重复条目的文件创建一个单独的&lt;execution/&gt;

    <executions>
      <execution>
        <id>jaxb-mac</id>
        <phase>generate-sources</phase>
        <goals>
          <goal>generate</goal>
        </goals>
        <configuration>
          <forceRegenerate>true</forceRegenerate>
          <generatePackage>my.company.mac</generatePackage>
          <schemaDirectory>src/main/schema</schemaDirectory>
          <schemaIncludes>
            <include>mac-3.4.xsd</include>
          </schemaIncludes>
        </configuration>
      </execution>
      <execution>
        <id>jaxb-stylesheet</id>
        <phase>generate-sources</phase>
        <goals>
          <goal>generate</goal>
        </goals>
        <configuration>
          <forceRegenerate>true</forceRegenerate>
          <generatePackage>my.company.stylesheet</generatePackage>
          <schemaDirectory>src/main/schema</schemaDirectory>
          <schemaIncludes>
            <include>mac-stylesheet-3.4.xsd</include>
          </schemaIncludes>
        </configuration>
      </execution>
    

    &lt;forceRegenerate&gt;true&lt;/forceRegenerate&gt; 很重要,否则只有第一个&lt;execution/&gt; 会运行,其余的会认为没有必要运行,因为我正在生成到同一目录中。

    我仍然想要一种劳动强度较低的解决方案来处理重复项。

    我认为,如果我将第一个主 .xsd 设为一个单独的模块,并构建到它自己的 .jar 文件中,那么我可以使用 &lt;episode/&gt; 标记并让它一遍又一遍地跳过生成相同的重复元素,因为它们是定义相同。

    我已经决定尽可能放弃 XML 和完全的 JAXB。截至本次编辑,有更新更好的方法来解析 XML 并将其映射到对象。

    【讨论】:

    • &lt;forceRegenerate&gt;maven-jaxb2-plugin:2.2 中不再可用。
    【解决方案2】:

    意识到这是旧的,但我有同样的错误,它可以通过不指定目标包解决它,即 xjc 的 -b 选项。然后每个重复的元素都在自己的命名空间包中创建并且没有冲突。

    【讨论】:

    • 评论强调这是 actual 答案,至少对我而言 - 在 pom 中删除我的 maven-jaxb2-plugin 配置中的 &lt;generatePackage&gt; 元素为我解决了同样的问题。
    • 最简单的解决方案!经过一番搜索后为我工作!
    • 能否请您发布您的 maven-jaxb2-plugin 配置。看来您的解决方案对我不起作用。
    【解决方案3】:

    我为 gradle 发布了我的解决方案,它解决了重复问题并且不需要 xjb 文件:

    task generateJaxb() {
        ext.sourcesDir = "${buildDir}/generated-sources/jaxb"
        ext.classesDir = "${buildDir}/classes/jaxb"
        ext.schemaDir = "src/resources/schemas"
        ext.tmp = "${buildDir}/tmp/xjc"
    
        doLast() {
            project.ant {
                taskdef name: "xjc", classname: "com.sun.tools.xjc.XJCTask",
                        classpath: configurations.jaxb.asPath
    
                delete(dir: tmp)
                mkdir(dir: tmp)
                delete(dir: sourcesDir)
                delete(dir: classesDir)
                mkdir(dir: sourcesDir)
                mkdir(dir: classesDir)
            }
    
            fileTree(schemaDir){
                include '**/*.xsd'
                include '**/*.wsdl'
            }.each{File file->
                //println file
                project.ant {
                    taskdef name: "xjc", classname: "com.sun.tools.xjc.XJCTask",
                            classpath: configurations.jaxb.asPath
                    xjc(destdir: tmp, schema:"${file.getAbsolutePath()}") {
                        arg(value: "-wsdl")
                        produces(dir: tmp, includes: "**/*.java")
                    }
                    copy(todir: sourcesDir) {
                        fileset(dir: tmp, erroronmissingdir: false) {
                            include(name: "**/*.java")
                        }
                    }
                    delete(dir: tmp)
                    mkdir(dir: tmp)
                }
            }
            project.ant {
                javac(destdir: classesDir, source: 1.6, target: 1.6, debug: true,
                        debugLevel: "lines,vars,source",
                        classpath: configurations.jaxb.asPath) {
                    src(path: sourcesDir)
                    include(name: "**/*.java")
                    include(name: "*.java")
                }
    
                copy(todir: classesDir) {
                    fileset(dir: sourcesDir, erroronmissingdir: false) {
                        exclude(name: "**/*.java")
                    }
                }
            }
        }
    }
    
    configurations {
        jaxb
    }
    
    dependencies {
        jaxb("com.sun.xml.bind:jaxb-xjc:2.2.4-1")
        compile(files(generateJaxb.classesDir).builtBy(generateJaxb))
    }
    
    jar {
        from generateJaxb.classesDir
    }
    

    【讨论】:

      【解决方案4】:

      &lt;schemaBindings&gt; 元素添加到 XSD:

      <schemaBindings>
          <package name="com.whatever.stuff" />
      </schemaBindings>
      

      Source

      【讨论】:

      • 我不想修改源.xsd,也无法让多个外部.xjb 文件工作,任何想法。我找不到关于如何将多个文件处理成多个包的清晰解释。
      • "我不想修改源 .xsd" - 为什么不呢?看起来很简单。这只是元数据。
      • 您的 .xjb 文件的根元素中有 xsi:schemaLocation=" http://java.sun.com/xml/ns/jaxb http://java.sun.com/xml/ns/jaxb/bindingschema_2_0.xsd" 吗?
      • 我终于弄清楚了名称空间问题,但这并没有真正解决我的问题的根本原因,即尝试处理重复的元素定义。我已经编辑了我的问题,以更好地反映将我带到这里的实际根本原因。
      • 如果任何.xsd 文件中有重复元素,这将失败,这最终是我的根本原因
      【解决方案5】:

      我们遇到了类似的问题:我们在同一个目录中有一个 wsdl 文件和两个 xsd 文件。 wsdl 文件导入两个 xsd 文件。问题是 JAXB 正在考虑所有三个文件并抛出“...已定义”错误。它基本上是在抱怨它在 wsdl 和 xsd 文件中看到了相同的元素。

      我们可以在 ma​​ven 插件配置(在 pom.xml 中) 中通过添加 exclude 标记来解决此问题,如下例所示:

          <build>
          <plugins>
              <plugin>
                  <groupId>org.jvnet.jaxb2.maven2</groupId>
                  <artifactId>maven-jaxb2-plugin</artifactId>
                  <version>0.12.3</version>
                  <executions>
                      <execution>
                          <goals>
                              <goal>generate</goal>
                          </goals>
                      </execution>
                  </executions>
                  <configuration>
                      <schemaLanguage>WSDL</schemaLanguage>
                      <generatePackage>mywsdl.wsdl</generatePackage>
                      <args><arg>-XautoNameResolution</arg></args>
                      <schemas>
                          <schema>
                              <fileset>
                                  <excludes>
                                      <exclude>*.xsd</exclude>
                                  </excludes>
                              </fileset>
                          </schema>
                      </schemas>
                  </configuration>
              </plugin>
          </plugins>
      </build>
      

      【讨论】:

        猜你喜欢
        • 2021-03-22
        • 1970-01-01
        • 2023-02-02
        • 2022-01-03
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2019-10-16
        • 2021-03-11
        相关资源
        最近更新 更多