Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/367.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java JAXB解组:对象列表_Java_Jaxb_Unmarshalling - Fatal编程技术网

Java JAXB解组:对象列表

Java JAXB解组:对象列表,java,jaxb,unmarshalling,Java,Jaxb,Unmarshalling,我有 对于的XML输入 public class Xlink { private String href; private String value; @XmlAttribute(namespace = "http://www.w3.org/1999/xlink") public String getHref() { return href; } public void setHref(String href)

我有

对于的XML输入

public class Xlink
{
    private String href;
    private String value;

    @XmlAttribute(namespace = "http://www.w3.org/1999/xlink")
    public String getHref()
    {
        return href;
    }

    public void setHref(String href)
    {
        this.href = href;
    }

    @XmlValue
    public String getValue()
    {
        return value;
    }

    public void setValue(String value)
    {
        this.value = value;
    }
}
Edit2:在对测试对象进行了一些解组和编组的实验之后,我发现我需要在内容的标题中定义xmlns名称空间,以便与
xlink:href=
类似
xmlns:xlink=”http://www.w3.org/1999/xlink"
问题在于,我从一个包装类中获取课程元素,该包装类由resteasy解析出来。因此,生成的类不会携带名称空间信息

我需要强迫JAXB理解
xmlns:xlink=”http://www.w3.org/1999/xlink“
适用于课程元素,但在谷歌搜索了一个小时后,我不知所措

Edit3:我正在从你那里拿到我的东西

在对应的服务器上使用。这反过来又是

我的解组代码的相关部分包括:

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<ns3:content xmlns:ns2="http://www.w3.org/1999/xlink" xmlns:ns3="http://www.w3.org/2005/Atom">
    <code>SOME CODE</code>
    <name>name</name>
    <subcourses>
        <course ns2:href="Some href">some value</course>
        <course ns2:href="sdsdg">sdfhdfhdhdh</course>
    </subcourses>
</ns3:content>
其中
r
是一个
javax.ws.rs.core.Response
。还有破译者

Feed f = r.readEntity(Feed.class);
out.addAll(unmarshaller.Unmarshal(f.getEntries(), clazz));
公共列表解组(列表条目、类类别)
{
List out=new ArrayList();
T例;
对于(条目e:条目)
{
尝试
{
JAXBContext context=JAXBContext.newInstance(clazz);
Unmarshaller unmarsh=context.createUnmarshaller();
实例=(T)unmarsh.unmarshal((节点)e.getContent());

因为这是我第一次使用这项技术,所以完全有可能这段代码是“wtf”。

当您注释字段(实例变量)时,请确保将
@xmlacessortype(xmlacesstype.field)
放在您的类上

public List<T> Unmarshal(List<Entry> entries, Class clazz)
{
    List<T> out = new ArrayList<T>();
    T instance;
    for (Entry e : entries)
    {
        try
        {
            JAXBContext context = JAXBContext.newInstance(clazz);
            Unmarshaller unmarsh = context.createUnmarshaller();
            instance = (T) unmarsh.unmarshal((Node) e.getContent());
有了我更新的
课程
类、您的
Xlink
类和一个正确的名称空间限定的XML文档,下面的演示代码对我来说非常适合

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

@XmlRootElement(namespace = "http://www.w3.org/2005/Atom", name = "content")
@XmlAccessorType(XmlAccessType.FIELD)
public class Course implements Resource {

    @XmlElementWrapper(name = "subcourses")
    @XmlElement(name = "course")
    List<Xlink> subcourses;

}

更新#1

Edit2:在进行了一些解包和编组的实验之后 我发现需要在中定义xmlns命名空间的测试对象 要匹配xlink:href=like的内容的标题 xmlns:xlink=”http://www.w3.org/1999/xlink“问题是我是 从解析的包装类内部获取课程元素 因此,生成的类不会继承 名称空间信息

解决问题的最佳方法是提取要解除marhal的片段

input.xml

下面是一个示例XML文档,其中名称空间信息定义在要解组的片段上方





更新#3

下面是您的示例代码的简化版本,其中所有内容都有效。也许您的代码中有一些不同之处,它将帮助您找到

条目

import javax.xml.bind.*;
import javax.xml.parsers.*;
import org.xml.sax.*;

public class Demo {

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

        // Create the XMLFilter
        XMLFilter filter = new NamespaceFilter();

        // Set the parent XMLReader on the XMLFilter
        SAXParserFactory spf = SAXParserFactory.newInstance();
        SAXParser sp = spf.newSAXParser();
        XMLReader xr = sp.getXMLReader();
        filter.setParent(xr);

        // Set UnmarshallerHandler as ContentHandler on XMLFilter
        Unmarshaller unmarshaller = jc.createUnmarshaller();
        UnmarshallerHandler unmarshallerHandler = unmarshaller
                .getUnmarshallerHandler();
        filter.setContentHandler(unmarshallerHandler);

        // Parse the XML
        InputSource xml = new InputSource("src/forum17766166/input.xml");
        filter.parse(xml);
        Course course = (Course) unmarshallerHandler.getResult();

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

}
演示

import javax.xml.bind.annotation.*;

@XmlRootElement(namespace="http://www.w3.org/2005/Atom")
@XmlAccessorType(XmlAccessType.FIELD)
public class Entry<T> {

    @XmlElement(namespace = "http://www.w3.org/2005/Atom")
    @XmlSchemaType(name = "atomInlineOtherContent")
    private T content;

    public T getContent() {
        return content;
    }

}
输出


一些价值
SDFHDHDH

你说的“拒绝解组”是什么意思?只是传递一个空列表?是的,每次0个项目。你能提供更多关于要解组的XML片段的来源的详细信息吗?尝试实现这一点时,出现了一个问题。我从响应中得到的是一个已经解析的XML节点的节点对象。我无法强制readEntity()它调用JAXB provider给我一个字符串对象。如果我试图将其强制转换为课程,它将抛出ElementsImpl无法强制转换为课程。我确信我在某个地方做错了什么,但不知道是什么。@Meltea-您可以解组
节点
对象。不,添加
@XmlAccessorType(XmlAccessType.FIELD)
只是给出了很多错误,比如
类有两个同名的属性
,而没有它,代码可以正常工作,并且有很多列表
import java.io.File;
import javax.xml.bind.*;

public class Demo {

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

        Unmarshaller unmarshaller = jc.createUnmarshaller();
        File xml = new File("src/forum17766166/input.xml");
        Course course = (Course) unmarshaller.unmarshal(xml);

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

}
import javax.xml.bind.*;
import javax.xml.stream.*;
import javax.xml.transform.stream.StreamSource;

public class Demo {

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

        XMLInputFactory xif = XMLInputFactory.newFactory();
        StreamSource source = new StreamSource("src/forum17766166/input.xml");
        XMLStreamReader xsr = xif.createXMLStreamReader(source);
        while(xsr.hasNext()) {
            if(xsr.isStartElement() && "content".equals(xsr.getLocalName())) {
                break;
            }
            xsr.next();
        }

        Unmarshaller unmarshaller = jc.createUnmarshaller();
        Course course = (Course) unmarshaller.unmarshal(xsr);

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

}
import org.xml.sax.*;
import org.xml.sax.helpers.*;

public class NamespaceFilter extends XMLFilterImpl {

    private static final String ATOM_URI = "http://www.w3.org/2005/Atom";
    private static final String XLINK_URI = "http://www.w3.org/1999/xlink";

    @Override
    public void startElement(String uri, String localName, String qName,
            Attributes atts) throws SAXException {
        if("atom:content".equals(qName)) {
            super.startElement(ATOM_URI, "content", qName, atts);
        } else if("course".equals(qName))  {
            AttributesImpl modifiedAtts = new AttributesImpl();
            modifiedAtts.addAttribute(XLINK_URI, "href", "xlink:href", null, atts.getValue(0));
            super.startElement(uri, localName, qName, modifiedAtts);
        } else {
            super.startElement(uri, localName, qName, atts);
        }
    }

    @Override
    public void endElement(String uri, String localName, String qName)
            throws SAXException {
        if("atom:content".equals(qName)) {
            super.endElement(ATOM_URI, "content", qName);
        } else {
            super.endElement(uri, localName, qName);
        }
    }

}
import javax.xml.bind.*;
import javax.xml.parsers.*;
import org.xml.sax.*;

public class Demo {

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

        // Create the XMLFilter
        XMLFilter filter = new NamespaceFilter();

        // Set the parent XMLReader on the XMLFilter
        SAXParserFactory spf = SAXParserFactory.newInstance();
        SAXParser sp = spf.newSAXParser();
        XMLReader xr = sp.getXMLReader();
        filter.setParent(xr);

        // Set UnmarshallerHandler as ContentHandler on XMLFilter
        Unmarshaller unmarshaller = jc.createUnmarshaller();
        UnmarshallerHandler unmarshallerHandler = unmarshaller
                .getUnmarshallerHandler();
        filter.setContentHandler(unmarshallerHandler);

        // Parse the XML
        InputSource xml = new InputSource("src/forum17766166/input.xml");
        filter.parse(xml);
        Course course = (Course) unmarshallerHandler.getResult();

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

}
import javax.xml.bind.annotation.*;

@XmlRootElement(namespace="http://www.w3.org/2005/Atom")
@XmlAccessorType(XmlAccessType.FIELD)
public class Entry<T> {

    @XmlElement(namespace = "http://www.w3.org/2005/Atom")
    @XmlSchemaType(name = "atomInlineOtherContent")
    private T content;

    public T getContent() {
        return content;
    }

}
import java.io.File;
import javax.xml.bind.*;
import org.w3c.dom.Node;

public class Demo {

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

        // Unmarshal Entry
        Unmarshaller unmarshaller = jc.createUnmarshaller();
        File xml = new File("src/forum17766166/input.xml");
        Entry entry = (Entry) unmarshaller.unmarshal(xml);

        // Unmarshal Course
        Node contentNode = (Node) entry.getContent();
        Course course = (Course) unmarshaller.unmarshal(contentNode);

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

}