我需要验证以编程方式生成的 XML 架构实例 (XSD) 文档,因此我使用了以下 Java 片段,它工作正常:
SchemaFactory factory = SchemaFactory.newInstance(
XMLConstants.W3C_XML_SCHEMA_NS_URI);
Schema xsdSchema = factory.newSchema( // Reads URL every time...
new URL("http://www.w3.org/2001/XMLSchema.xsd"));
Validator xsdValidator = xsdSchema.newValidator();
xsdValidator.validate(new StreamSource(schemaInstanceStream));
但是,当我保存 XML Schema definition file本地并以这种方式引用它:
Schema schema = factory.newSchema(
new File("test/xsd/XMLSchema.xsd"));
失败并出现以下异常:
org.xml.sax.SAXParseException: schema_reference.4: Failed to read schema document 'file:/Users/foo/bar/test/xsd/XMLSchema.xsd', because 1) could not find the document; 2) the document could not be read; 3) the root element of the document is not <xsd:schema>.
我已通过对 File
对象执行 exists()
和 canRead()
断言来确保文件存在并且可读。我还使用几个不同的实用程序(网络浏览器、wget)下载了该文件,以确保没有损坏。
知道为什么当我从 HTTP URL 生成模式时我可以验证 XSD 实例文档,但是当我尝试从具有相同内容的本地文件生成时我得到上述异常吗?
[编辑]
为了详细说明,我尝试了多种形式的 factory.newSchema(...)
使用 Readers 和 InputStreams(而不是直接使用 File),但仍然得到完全相同的错误。此外,我在使用它或各种输入流之前转储了文件内容以确保它是正确的。挺烦人的。
完整答案
事实证明,XML Schema 引用的另外三个文件也必须存储在本地,并且 XMLSchema.xsd
包含一个必须更改其 schemaLocation
属性的导入语句.以下是必须保存在同一目录中的文件:
- XMLSchema.xsd - 在 XML 命名空间的“导入”元素中将
schemaLocation
更改为“xml.xsd
”。 - XMLSchema.dtd - 原样。
- datatypes.dtd - 原样。
- xml.xsd - 原样。
感谢@Blaise Doughan 和@Tomasz Nurkiewicz 的提示。
最佳答案
我假设您正在尝试加载 XMLSchema.xsd .另请下载XMLSchema.dtd和 datatypes.dtd并将它们放在同一个目录中。这应该会让您更进一步。
关于java - 从 URL 创建 XML 模式有效但从本地文件创建失败?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/7249316/