问题 JAXB:使用同一元素的多个名称解组xml


我认为这对于真正了解JAXB绑定文件的人来说很容易...

基本问题

如何配置JAXB以将多个元素解组到同一个类中?

注意:我想避免为我的项目添加另一个依赖项(如MOXy)。理想情况下,这可以通过注释或自定义绑定文件来完成。

背景

我有一个XML文档,其中包含相同元素的许多变体 - 每个变体具有完全相同的属性。使用下面的示例,我关心的只是“员工”,但XML指定“董事,经理和员工”。出于我们的目的,这些都是同一父类的子类,我们只需要使用父类型(Employee),并且我们的对象模型没有或不需要子类的实例。

我希望JAXB绑定任何实例 director, manager, or staff 元素成一个 Employee 目的。 

输入:

<organization>
    <director>
        <fname>Dan</fname>
        <lname>Schman</lname>
    </director>    
    <manager>
        <fname>Joe</fname>
        <lname>Schmo</lname>
    </manager>    
    <staff>
        <fname>Ron</fname>
        <lname>Schwan</lname>
    </staff>    
    <staff>
        <fname>Jim</fname>
        <lname>Schwim</lname>
    </staff>    
    <staff>
        <fname>Jon</fname>
        <lname>Schwon</lname>
    </staff>    
</organization>

输出:

在解组这个例子后,我最终会得到一个 Organization 具有一个属性的对象: List<Employees> employees 其中每个员工只有firstName和lastName。

(注意:每个员工都是类型 Employee 不 Director/Manager/Staff。解组时,子类信息将丢失。我们也不关心编组 - 我们只需要从XML创建对象)

这可以在没有MOXy这样的扩展的情况下完成吗?自定义bindings.xjb文件可以保存一天吗?


3894
2018-06-20 21:06


起源

希望@BlaiseDoughan会看到你的问题,因为他最近在这个网站上很活跃,而且他和任何人都知道他的JAXB。 他的博客 值得一读。 - Hovercraft Full Of Eels
那太好了。如果是这样的话...我有各种各样的赞成和代表他们的名字! ;) - gMale


答案:


这对应于选择结构。你可以使用 @XmlElements 此用例的注释:

@XmlElements({
    @XmlElement(name="director", type=Employee.class),
    @XmlElement(name="manager", type=Employee.class)
})
List<Employee> getEmployees() {
    return employees;
}

如果您从XML模式开始,以下内容将有所帮助:


15
2018-06-20 21:21



你,先生,是个天才!像魅力一样工作! - gMale
作为后续:是否有任何简单的方法来保留原始元素名称(比如将其作为属性传递给正在创建的对象)? - gMale
在JAXB中,您可以将结果包装在一个 JAXBElement。将该值存储在属性中的能力是我们考虑添加到MOXy的。 - Blaise Doughan
是时候回去研究你的博客了! 1+ - Hovercraft Full Of Eels
@BigBen - 我看到你已经想到了这个: stackoverflow.com/a/15917708/383861 (我给你的问题和答案+1)。 - Blaise Doughan