【问题标题】:xercesJ for XSD 1.1: Validator correctly processes assertions, SAXParser apparently does notxercesJ for XSD 1.1:Validator 正确处理断言,SAXParser 显然没有
【发布时间】:2014-06-05 08:59:41
【问题描述】:

我正在为我的 java 项目构建一个 xml 验证器 xerces-2_11_0-xml-schema-1.1-beta 库,以支持 XSD 1.1 的特定功能,如断言。

考虑到这个架构

<?xml version="1.1" encoding="UTF-8"?>
<schema targetNamespace="http://www.example.org/Example" elementFormDefault="qualified" xmlns="http://www.w3.org/2001/XMLSchema" xmlns:tns="http://www.example.org/Example">

    <complexType name="NodeType">
        <sequence>
            <element name="Node" type="tns:NodeType"
                maxOccurs="unbounded" minOccurs="0">
            </element>
        </sequence>
        <attribute name="partnumber">
            <simpleType>
                <restriction base="string">
                    <pattern value="[A-Z0-9_\-]+"></pattern>
                </restriction>
            </simpleType>
        </attribute>
        <assert test="starts-with(@partnumber,../@partnumber)"/>
    </complexType>

    <element name="Node" type="tns:NodeType"></element>
</schema>

我开始使用“javax.xml.validation.Validator”类

...
StreamSource xmlSource = new StreamSource(new File("example.xml"));

SchemaFactory sf = SchemaFactory.newInstance("http://www.w3.org/XML/XMLSchema/v1.1");
Schema s = sf.newSchema(new File("example.xsd"));

Validator v = s.newValidator();
v.setErrorHandler(new MyErrorHandler())
v.validate(xmlSource)
...

private static class MyErrorHandler extends DefaultHandler {

...
        public void error(SAXParseException e) throws SAXException {
            System.out.println("Error: "); 
            System.out.println("   Public ID: "+e.getPublicId());
            System.out.println("   System ID: "+e.getSystemId());
            System.out.println("   Line number: "+e.getLineNumber());
            System.out.println("   Column number: "+e.getColumnNumber());
            System.out.println("   Message: "+e.getMessage());;
        }
...
}

此解决方案有效:example.xsd 中的断言测试得到正确处理,xml 文件的验证运行顺利(断言测试得到正确评估)

然后我用 SAXParser 替换了 Validator(原因:更好地控制 sax 解析阶段)

...
SchemaFactory sf = SchemaFactory.newInstance("http://www.w3.org/XML/XMLSchema/v1.1");
Schema s = sf.newSchema(new File("example.xsd"));

SAXParserFactory spf = SAXParserFactory.newInstance();
spf.setSchema(s);
spf.setNamespaceAware(true);
spf.setValidating(true);
spf.setFeature("http://apache.org/xml/features/validation/schema", true);

SAXParser parser = spf.newSAXParser();
XMLReader r = parser.getXMLReader();
r.setErrorHandler(new MyErrorHandler())
r.parse("example.xml");
...

在第二种情况下,解析阶段在 xsd "assert" 子句上遇到错误,并显示以下消息:

s4s-elt-invalid-content.1: The content of 'NodeType' is invalid.  Element 'assert' is invalid, misplaced, or occurs too often.

如果我删除 example.xsd 中的 assert 子句(从而使其符合 1.0)验证运行正确,所以我认为 SAXParser 仍在使用 1.0 规范。

为了遵守 1.1 模式规则,我在配置 SAXParserFactory 或 SAXParser 本身时是否遗漏了什么?

【问题讨论】:

    标签: java xml validation xsd


    【解决方案1】:

    我认为您的项目中缺少 XPATH 2.0 依赖项。请检查一下!

    XML Schema 1.1 'assertions' 和 'type Alternatives' 需要 XPath 2.0 处理器进行评估。对于 XSD 1.1 断言,需要完整的 XPath 2.0 支持。对于 XSD 1.1 类型的替代方案,XML 模式引擎 可以提供完整的 XPath 2.0 支持,或者他们可以实现更小的 XPath 2.0 子集,由 XSD 1.1 语言定义。

    来自: http://xerces.apache.org/xerces2-j/faq-xs.html

    【讨论】:

    • 考虑到同一个项目中的验证器可以工作,并且我认为它利用了相同的 XPath 处理器。所以我认为依赖关系是正确的:我的项目引用了“org.eclipse.wst.xml。 xpath2.processor" jar 与 "xerces-2_11_0-xml-schema-1.1-beta" 包捆绑在一起,我想它包含 XPath 2.0 处理器
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-12-30
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多