XML 当架构文件位于 WAR 时针对 XSD 进行验证
XML validation against XSDs when schema files locate in a WAR
我正在尝试验证 XML 与乘 XSD 模式的对比。
如果我将我的应用程序作为一个简单的 Spring-启动应用程序来执行,那么下面的代码就像一个魅力:
// init
String[] xsdFileNames = ...
Source[] sources = new Source[xsdFileNames.length];
for (int i = 0; i < xsdFileNames.length; i++) {
InputStream inputStream = Thread.currentThread().getContextClassLoader().getResourceAsStream(xsdFileNames[i]);
String realPath = getClass().getClassLoader().getResource(xsdFileNames[i]).getFile();
StreamSource streamSource = new StreamSource(inputStream);
streamSource.setSystemId(realPath );
sources[i] = streamSource;
}
SchemaFactory schemaFactory = SchemaFactory.newInstance(XMLConstants.W3C_XML_SCHEMA_NS_URI);
Schema schema = schemaFactory.newSchema(sources);
validator = schema.newValidator();
// validate
String xmlString = ...
StringReader xmlStringReader = new StringReader(xmlString))
Source source = new StreamSource(xmlStringReader);
validator.validate(source);
需要设置StreamSource
的systemId
否则SAXParser
看不到来自第二个XSD的XSD类型。更多信息 .
但不幸的是,我的 WAR 需要在 Oracle WebLogic Server 中 运行,并且因为 WebLogic 对来自 WAR 的文件进行了欺骗,所以上面的解决方案不起作用。
WebLogic 将资源文件打包到 _wl_cls_gen.jar
中,并且 javax.xml.transform.Source
无法用这个神奇的 jar 解析路径:.../_wl_cls_gen.jar!/schema/main.xsd
.
在 javax.xml.transform.Source
里面有一个 java.io.File
并且它没有遵循这条奇怪的路径。
这是 realPath
变量在 Spring-Boot:
情况下的值
/home/xxx/dev/workspace/java/xxx/target/classes/schema/main.xsd
对于 WebLogic:
/u01/oracle/user_projects/domains/DEV_DOMAIN/servers/ADMIN_SERVER/tmp/_WL_user/demo-0.1.0/g369dl/war/WEB-INF/lib/_wl_cls_gen.jar!/schema/main.xsd
知道如何处理吗?
您可以使用类加载器从 *.war 中加载文件,例如
getClass().getClassLoader().getResourceAsStream("/resources/myfile.xsd");
尝试在 weblogic.xml
中使用 show-archived-real-path-enabled
show-archived-real-path-enabled The show-archived-real-path-enabled
element specifies the behavior of getRealPath() for archived Web
applications.
When set to true, getRealPath() returns the canonical path of the
resource files.
If the show-archived-real-path-enabled element is set to false, the
servlet container will return the real path of files in archived Web
applications as null.
The default value is false.
https://docs.oracle.com/cd/E24329_01/web.1211/e21049/weblogic_xml.htm#WBAPP611
我正在尝试验证 XML 与乘 XSD 模式的对比。
如果我将我的应用程序作为一个简单的 Spring-启动应用程序来执行,那么下面的代码就像一个魅力:
// init
String[] xsdFileNames = ...
Source[] sources = new Source[xsdFileNames.length];
for (int i = 0; i < xsdFileNames.length; i++) {
InputStream inputStream = Thread.currentThread().getContextClassLoader().getResourceAsStream(xsdFileNames[i]);
String realPath = getClass().getClassLoader().getResource(xsdFileNames[i]).getFile();
StreamSource streamSource = new StreamSource(inputStream);
streamSource.setSystemId(realPath );
sources[i] = streamSource;
}
SchemaFactory schemaFactory = SchemaFactory.newInstance(XMLConstants.W3C_XML_SCHEMA_NS_URI);
Schema schema = schemaFactory.newSchema(sources);
validator = schema.newValidator();
// validate
String xmlString = ...
StringReader xmlStringReader = new StringReader(xmlString))
Source source = new StreamSource(xmlStringReader);
validator.validate(source);
需要设置StreamSource
的systemId
否则SAXParser
看不到来自第二个XSD的XSD类型。更多信息
但不幸的是,我的 WAR 需要在 Oracle WebLogic Server 中 运行,并且因为 WebLogic 对来自 WAR 的文件进行了欺骗,所以上面的解决方案不起作用。
WebLogic 将资源文件打包到 _wl_cls_gen.jar
中,并且 javax.xml.transform.Source
无法用这个神奇的 jar 解析路径:.../_wl_cls_gen.jar!/schema/main.xsd
.
在 javax.xml.transform.Source
里面有一个 java.io.File
并且它没有遵循这条奇怪的路径。
这是 realPath
变量在 Spring-Boot:
/home/xxx/dev/workspace/java/xxx/target/classes/schema/main.xsd
对于 WebLogic:
/u01/oracle/user_projects/domains/DEV_DOMAIN/servers/ADMIN_SERVER/tmp/_WL_user/demo-0.1.0/g369dl/war/WEB-INF/lib/_wl_cls_gen.jar!/schema/main.xsd
知道如何处理吗?
您可以使用类加载器从 *.war 中加载文件,例如
getClass().getClassLoader().getResourceAsStream("/resources/myfile.xsd");
尝试在 weblogic.xml
中使用 show-archived-real-path-enabledshow-archived-real-path-enabled The show-archived-real-path-enabled element specifies the behavior of getRealPath() for archived Web applications.
When set to true, getRealPath() returns the canonical path of the resource files.
If the show-archived-real-path-enabled element is set to false, the servlet container will return the real path of files in archived Web applications as null.
The default value is false.
https://docs.oracle.com/cd/E24329_01/web.1211/e21049/weblogic_xml.htm#WBAPP611