简体   繁体   English

将XML文件编组到Java pojo /域对象

[英]Marshalling XML file to Java pojo/domain object

I have an old Access database that is basically one flat file. 我有一个旧的Access数据库,基本上是一个平面文件。 I want to migrate the data to my new whizzy, object oriented, hibernate based wonder-app. 我想将数据迁移到我的新的,面向对象的,基于休眠的神奇应用程序。

The data is available as an XML file, and I want to map to three separate java pojos. 数据以XML文件形式提供,我想映射到三个单独的java pojos。 I planned on using JAXB to do this, specifically using @xmlelement annotation. 我计划使用JAXB来做到这一点,特别是使用@xmlelement批注。 However the structure of the XML file is not optimal, in my pojos I have split up the data into three different objects. 但是XML文件的结构不是最佳的,在我的实验中,我将数据分为三个不同的对象。

Will JAXB help with this ? JAXB可以帮上忙吗? Do I need to simply create java pojo based on existing schema/xml file (that is not oo) using jaxb. 我是否需要使用jaxb根据现有的schema / xml文件(不是oo)简单地创建java pojo。 Then create apdater classes/layer to put the data into my three pojos ? 然后创建apdater类/层以将数据放入我的三个pojo中? Or can I map straight from the xml file to 3 pojos with correct config/annotation ? 或者我可以使用正确的配置/注释直接从xml文件映射到3个pojos?

Note: I'm the EclipseLink JAXB (MOXy) lead and a member of the JAXB 2 (JSR-222) expert group. 注意:我是EclipseLink JAXB(MOXy)的负责人,并且是JAXB 2(JSR-222)专家组的成员。

Assuming your XML document looks something like the following: 假设您的XML文档如下所示:

<?xml version="1.0" encoding="UTF-8"?>
<rows>
    <row>
        <col1>a1</col1>
        <col2>b1</col2>
        <col3>c1</col3>
    </row>
    <row>
        <col1>a1</col1>
        <col2>b2</col2>
        <col3>c2</col3>
    </row>
</rows>

You could leverage MOXy's @XmlPath annotation and do something like. 您可以利用MOXy的@XmlPath注释并执行类似的操作。 EclipseLink also includes a JPA implementation : EclipseLink还包括一个JPA实现

Rows 行数

You will need to create a Root object to hold everything: 您将需要创建一个Root对象来保存所有内容:

package forum8577359;

import java.util.List;
import javax.xml.bind.annotation.*;

@XmlRootElement
@XmlAccessorType(XmlAccessType.FIELD)
public class Rows {

    @XmlElement(name="row")
    private List<A> rows;

}

A 一种

Since the contents for the A , B , and C objects are all at the same level you can use MOXy's @XmlPath annotation and specify the "." 由于ABC对象的内容都处于同一级别,因此可以使用MOXy的@XmlPath批注并指定"." XPath. XPath。 This tells MOXy that the object, and the object it is referencing occur at the same level: 这告诉MOXy该对象及其引用的对象在同一级别发生:

package forum8577359;

import javax.xml.bind.annotation.*;
import org.eclipse.persistence.oxm.annotations.XmlPath;

@XmlAccessorType(XmlAccessType.FIELD)
public class A {

    private String col1;

    @XmlPath(".")
    private B b;

}

B

Again we use @XmlPath(".") to map the relationship between B and C : 同样,我们使用@XmlPath(".")映射BC之间的关系:

package forum8577359;

import javax.xml.bind.annotation.*;
import org.eclipse.persistence.oxm.annotations.XmlPath;

@XmlAccessorType(XmlAccessType.FIELD)
public class B {

    private String col2;

    @XmlPath(".")
    private C c;

}

C C

package forum8577359;

import javax.xml.bind.annotation.*;

@XmlAccessorType(XmlAccessType.FIELD)
public class C {

    private String col3;

}

Demo 演示版

The following demo code can be used to run this example: 以下演示代码可用于运行此示例:

package forum8577359;

import java.io.File;
import javax.xml.bind.*;

public class Demo {

    public static void main(String[] args) throws Exception {
        JAXBContext jc = JAXBContext.newInstance(Rows.class);

        Unmarshaller unmarshaller = jc.createUnmarshaller();
        File xml = new File("src/forum8577359/input.xml");
        Rows rows = (Rows) unmarshaller.unmarshal(xml);

        Marshaller marshaller = jc.createMarshaller();
        marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true);
        marshaller.marshal(rows, System.out);
    }

}

jaxb.properties jaxb.properties

To specify MOXy as your JAXB provider you need to include a jaxb.properties file in the same package as your domain classes with the following entry: 要将MOXy指定为JAXB提供程序,您需要在与域类相同的包中包含jaxb.properties文件,并带有以下条目:

javax.xml.bind.context.factory = org.eclipse.persistence.jaxb.JAXBContextFactory

For More Information 欲获得更多信息

在不知道问题具体细节的情况下...这是有可能的,但是听起来这可能是您想要编写模式,使用xjc生成绑定对象,解组到所生成的绑定对象然后进行翻译的情况Java中的域对象(或在适用时直接使用生成的对象)。

Typically JAXB helps. 通常,JAXB会有所帮助。 Even if you are writing classes and annotations manually I think it takes less time than parsing using DOM API. 即使您是手动编写类和批注,我认为它也比使用DOM API进行分析花费的时间更少。

Moreover you can generate value objects automatically using JAXB. 此外,您可以使用JAXB自动生成值对象。 I think this is the approach you should try. 我认为这是您应该尝试的方法。 First you should generate XSD file from your XML (unless you already have one). 首先,您应该从XML生成XSD文件(除非您已经拥有一个)。 Then you should generated value objects based on the XSD. 然后,您应该基于XSD生成值对象。 Then just parse the file. 然后只需解析文件。 2 code lines and you are done. 2条代码行,您就完成了。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM