针对模式的XML验证在带有命名空间的Java中失败

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了针对模式的XML验证在带有命名空间的Java中失败相关的知识,希望对你有一定的参考价值。

我需要编写针对模式验证XML的Java代码。由于某些我无法理解的原因验证失败,给出以下异常:

org.xml.sax.SAXParseException; cvc-elt.1: Cannot find the declaration of element 'root'

架构:

<?xml version="1.0" encoding="UTF-8"?>
<xs:schema elementFormDefault="qualified"
    targetNamespace="http://www.example.com"
    xmlns="http://www.example.com"
    xmlns:xs="http://www.w3.org/2001/XMLSchema">
    <xs:element name="root" type="rootType"/>
    <xs:simpleType name="rootType">
        <xs:restriction base="xs:integer"/>
    </xs:simpleType>
</xs:schema>

XML:

<?xml version="1.0" encoding="UTF-8"?>
<root xmlns="http://www.example.com">1</root>

Java代码:

try (InputStream xmlStream = Main.class.getClassLoader().getResourceAsStream("a.xml");
        InputStream xsdStream = Main.class.getClassLoader().getResourceAsStream("a.xsd")) {
    DocumentBuilder parser = DocumentBuilderFactory.newInstance().newDocumentBuilder();
    Document document = parser.parse(xmlStream);
    SchemaFactory factory = SchemaFactory.newInstance(XMLConstants.W3C_XML_SCHEMA_NS_URI);
    StreamSource schemaFile = new StreamSource(xsdStream);
    Schema schema = factory.newSchema(schemaFile);
    Validator validator = schema.newValidator();
    validator.validate(new DOMSource(document));
}

如果我删除对命名空间“http://www.example.com”的所有引用,则验证成功。架构,XML或代码有什么问题吗?

答案

您应该在构建器工厂中启用名称空间。

    DocumentBuilderFactory fact = DocumentBuilderFactory.newInstance();
    fact.setNamespaceAware(true);
    DocumentBuilder parser = fact.newDocumentBuilder();
另一答案

您应该使用DocumentBuilderFactory方法使setNamespaceAware()名称空间感知。

以上是关于针对模式的XML验证在带有命名空间的Java中失败的主要内容,如果未能解决你的问题,请参考以下文章

错误配置:找不到 XML 模式命名空间的 Spring NamespaceHandler

从 XElement 创建带有名称空间和模式的 XML

Spring,JMS - 无法找到 XML 模式命名空间的 Spring NamespaceHandler

xquery 转换在元素中创建空命名空间

Jaxb:在同一个包中解组具有多个命名空间的 xml

JAXB:为啥在生成的 xml 文档中未使用定义的命名空间前缀?