1

我在验证 Java 中的 XML 文件时遇到问题,我不断收到“无效类型”错误。我一直在谷歌搜索并找到了一些 SO 线程,它们告诉我在 XML 中添加名称空间并在任何地方添加“ns:”,但无济于事。

XML:

<ns:Content xmlns:ns="http://namespace">
  <ns:Request>
    <ns:FromDateTime>20130726161606</ns:FromDateTime>
    <ns:RemainderOffset/>
    <ns:MaxResults>100</ns:MaxResults>
  </ns:Request>
  <ns:Response>
    <ns:Status>
      <ns:Code>200</ns:Code>
    </ns:Status>
    <ns:Remainder>
      <ns:Count>2828</ns:Count>
      <ns:Offset>126690959</ns:Offset>
    </ns:Remainder>
    <ns:Items>
      <ns:Item id="126752560" itemHash="-1686318559">
        <ns:Title>[…]</ns:Title>
        <ns:Description>[…]</ns:Description>
        <ns:PubDate>Thu, 05 Sep 2013 06:00:27 GMT</ns:PubDate>
        <ns:Uri>[…]</ns:Uri>
        <ns:Resource>[…]</ns:Resource>
        <ns:Keywords>
          <ns:Keyword>[…]</ns:Keyword>
        </ns:Keywords>
      </ns:Item>
    </ns:Items>
  </ns:Response>
</ns:Content>

架构:

<?xml version="1.0" encoding="UTF-8"?>
<xs:schema xmlns="http://namespace"
       xmlns:xs="http://www.w3.org/2001/XMLSchema"
       targetNamespace="http://namespace"
       elementFormDefault="qualified" attributeFormDefault="unqualified">
<xs:element name="Content">
    <xs:complexType>
        <xs:sequence>
            <xs:element name="Request">
                <xs:complexType>
                    <xs:sequence>
                        <xs:element type="xs:long" name="FromDateTime"/>
                        <xs:element type="xs:string" name="RemainderOffset"/>
                        <xs:element type="xs:int" name="MaxResults"/>
                    </xs:sequence>
                </xs:complexType>
            </xs:element>
            <xs:element name="Response">
                <xs:complexType>
                    <xs:sequence>
                        <xs:element name="Status">
                            <xs:complexType>
                                <xs:sequence>
                                    <xs:element type="xs:short" name="Code"/>
                                </xs:sequence>
                            </xs:complexType>
                        </xs:element>
                        <xs:element name="Remainder">
                            <xs:complexType>
                                <xs:sequence>
                                    <xs:element type="xs:int" name="Count"/>
                                    <xs:element type="xs:int" name="Offset"/>
                                </xs:sequence>
                            </xs:complexType>
                        </xs:element>
                        <xs:element name="Items">
                            <xs:complexType>
                                <xs:sequence>
                                    <xs:element name="Item" maxOccurs="unbounded" minOccurs="0">
                                        <xs:complexType>
                                            <xs:sequence>
                                                <xs:element type="xs:string" name="Title"/>
                                                <xs:element type="xs:string" name="Description"/>
                                                <xs:element type="xs:string" name="PubDate"/>
                                                <xs:element type="xs:anyURI" name="Uri"/>
                                                <xs:element type="xs:string" name="Resource"/>
                                                <xs:element name="Keywords">
                                                    <xs:complexType mixed="true">
                                                        <xs:sequence>
                                                            <xs:element type="xs:string" name="Keyword" maxOccurs="unbounded" minOccurs="0"/>
                                                        </xs:sequence>
                                                    </xs:complexType>
                                                </xs:element>
                                            </xs:sequence>
                                            <xs:attribute type="xs:int" name="id"  use="required"/>
                                            <xs:attribute type="xs:int" name="itemHash" use="required"/>
                                        </xs:complexType>
                                    </xs:element>
                                </xs:sequence>
                            </xs:complexType>
                        </xs:element>
                    </xs:sequence>
                </xs:complexType>
            </xs:element>
        </xs:sequence>
    </xs:complexType>
</xs:element>

当然还有我用来读取文件的代码。这是我首先下载的文件,它以Object o. 我认为错误出在某个地方,因为 XML 使用在线工具验证了这个模式……为了便于阅读,我删除了 try-catch 块。

main method {
    File file = (File) o;
    DocumentBuilderFactory f = DocumentBuilderFactory.newInstance();

    DocumentBuilder b = f.newDocumentBuilder();
    Document doc = b.parse(file.getAbsolutePath());
    doc.getDocumentElement().normalize();


    // Add the correct namespace to the xml so there won't be any false positive errors
    // Got this part from SO
    Element originalDocumentElement = doc.getDocumentElement();
    Element newDocumentElement = doc.createElementNS(NAMESPACE, originalDocumentElement.getNodeName());
    newDocumentElement.setPrefix("ns");
    NodeList list = originalDocumentElement.getChildNodes();
    while(list.getLength()!=0) {
        newDocumentElement.appendChild(list.item(0));
    }
    // Replace the original element
    doc.replaceChild(newDocumentElement, originalDocumentElement);

    xmlOptions = createXmlOptions();
    xmlDoc = XmlObject.Factory.parse(doc, xmlOptions);
    validate();
}
public XmlOptions createXmlOptions()
{
    Map<String, String> substituteNamespaces = new HashMap<String, String>();
    substituteNamespaces.put("", "http://namespace");
    XmlOptions xmlOptions = new XmlOptions();
    xmlOptions.setLoadSubstituteNamespaces(substituteNamespaces);
    xmlOptions.setCharacterEncoding(FILE_ENCODING);
    xmlOptions.setErrorListener(errors);
    xmlOptions.setValidateTreatLaxAsSkip();
    return xmlOptions;
}

public boolean validate() throws ParserException {

    return xmlDoc.validate(xmlOptions);
}

错误消息:错误:cvc-elt.1:无效类型

打印error.getCursorLocation().xmlText()返回整个 XML 文件。

4

3 回答 3

2

架构用于命名空间

targetNamespace="http://red.persgroep.be/technology/1.0"

它与命名空间中的文档无关

xmlns:ns="http://namespace"

您只能根据适用于元素名称空间的架构来验证元素。

于 2013-09-06T10:34:01.093 回答
1
<ns:EndDateTime/>

是一个EndDateTime值为空字符串的元素,我认为这对于类型为xs:long. 您已将元素同时声明为minOccurs="0"and nillable="true",因此您有两种表示不存在EndDateTime值的方法 - 您可以完全不使用该元素,也可以使用将其标记为 nil

<ns:EndDateTime xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                xsi:nil="true"/>
于 2013-09-06T10:51:17.340 回答
0

我仍然不知道为什么会出现此错误,但对于面临相同问题的任何人:使用XML Beans。非常容易设置,甚至更容易使用。我能够重用我的很多代码并且它立即工作。

于 2013-09-06T14:45:00.667 回答