DOCTYPE 已弃用,Xinclude 不这样做
DOCTYPE is deprecated and Xinclude does not do it
我需要一种方法来包含不包含全局 opening/closing tag/element 的零散 XML。该片段正在增长,因为程序不时将数据(更多块)附加到其中,因此它既没有结束标记也没有开始标记。我已经将 !DOCTYPE 与 !ENTITY 一起使用,但这已被弃用,新的 Xinclude 似乎无法导入它,因为它强制片段具有 "one" 开始和结束标记。
更多信息:以下内容适用于 IE-10,但不适用于 IE-11。后者不导入文件 current.log.
注意:根据此网站,Microsoft Edge 不支持它:https://docs.microsoft.com/en-us/internet-explorer/ie11-deploy-guide/deprecated-document-modes
<?xml version='1.0' encoding='ISO-8859-1'?>
<?xml-stylesheet type='text/xsl' href='IndexLog.xsl'?>
<!DOCTYPE myRoot [<!ENTITY thisMonthLog SYSTEM "current.log">]>
<myRoot>
&thisMonthLog;
</myRoot>
日志 current.log 看起来像这样:
<block>
<a>any text</a>
<b>any text</b>
<c>any text</c>
<d>any text</d>
<e>any text</e>
</block>
<block>
<a>any text</a>
<b>any text</b>
<c>any text</c>
<d>any text</d>
<e>any text</e>
</block>
根据您的意见,我了解到您直接使用 IE 11 从文件系统加载 XML 文档。我认为 IE 已转而使用 MSXML 6 而不是 MSXML 3 默认用于 XSLT 和 MSXML 6 默认禁止 DTD 并且不加载外部实体。我知道绕过它的唯一方法是将 MSXML 6 与脚本一起使用并设置它必须允许 DTD 的属性,加载外部资源(对于您的情况,因为 DTD 仅用于加载外部资源实体,禁用验证):
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
version="1.0">
<xsl:output method="html" indent="yes" version="5" doctype-system="about:legacy-doctype"/>
<xsl:template match="/">
<html>
<head>
<title>Test</title>
<script>
function runXslt(xmlUri, xsltUri, targetElement) {
var xmlDoc = new ActiveXObject('Msxml2.DOMDocument.6.0');
xmlDoc.async = false;
xmlDoc.resolveExternals = true;
xmlDoc.validateOnParse = false;
xmlDoc.setProperty('ProhibitDTD', false);
xmlDoc.load(xmlUri);
var xsltDoc = new ActiveXObject('Msxml2.DOMDocument.6.0');
xsltDoc.async = false;
xsltDoc.load(xsltUri);
targetElement.insertAdjacentHTML('beforeEnd', xmlDoc.documentElement.transformNode(xsltDoc));
}
</script>
<script>
document.addEventListener(
'DOMContentLoaded',
function() {
runXslt('test201706070101.xml', 'test2017060701.xsl', document.body);
},
false
);
</script>
</head>
<body>
<h1>Test</h1>
</body>
</html>
</xsl:template>
<xsl:template match="myRoot">
<section>
<h2>Content</h2>
<xsl:apply-templates/>
</section>
</xsl:template>
<xsl:template match="block">
<ul>
<xsl:apply-templates/>
</ul>
</xsl:template>
<xsl:template match="block/*">
<li>
<xsl:apply-templates/>
</li>
</xsl:template>
</xsl:stylesheet>
这样的话,如果输入文档test201706070101.xml
的内容是
<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/xsl" href="test2017060701.xsl"?>
<!DOCTYPE myRoot [
<!ENTITY thisMonthLog SYSTEM "test201706070102.xml">
]>
<myRoot>
&thisMonthLog;
</myRoot>
在 IE 11 中加载并启用脚本,解析完整日志,例如第二个文件有
<?xml version="1.0" encoding="UTF-8"?>
<block>
<a>any text</a>
<b>any text</b>
<c>any text</c>
<d>any text</d>
<e>any text</e>
</block>
<block>
<a>any text</a>
<b>any text</b>
<c>any text</c>
<d>any text</d>
<e>any text</e>
</block>
并且样式表已经post编辑,IE window 中的输出是
Test
Content
•any text
•any text
•any text
•any text
•any text
•any text
•any text
•any text
•any text
•any text
所以外部实体已经加载。主要缺点显然是需要脚本,另一个缺点是使用的带有 MSXML 和 ActiveXObject 的脚本与 Edge 不兼容,因为它不支持 ActiveXObject.
我 post 这个答案是关于如果您想依靠 IE 进行 XSLT 转换可能有帮助的建议,从长远来看,将 XSLT 移动到 HTML 转换可能会更好到 .NET 这样的平台,您可以在其中更好地控制 XML 解析和 XSLT 处理的交互方式。
示例文件在 https://martin-honnen.github.io/xslt/2017/test201706070101.xml, https://martin-honnen.github.io/xslt/2017/test201706070102.xml and https://martin-honnen.github.io/xslt/2017/test2017060701.xsl 上在线,但我知道您想在本地而不是通过 HTTP(S) 执行此操作。
我需要一种方法来包含不包含全局 opening/closing tag/element 的零散 XML。该片段正在增长,因为程序不时将数据(更多块)附加到其中,因此它既没有结束标记也没有开始标记。我已经将 !DOCTYPE 与 !ENTITY 一起使用,但这已被弃用,新的 Xinclude 似乎无法导入它,因为它强制片段具有 "one" 开始和结束标记。
更多信息:以下内容适用于 IE-10,但不适用于 IE-11。后者不导入文件 current.log.
注意:根据此网站,Microsoft Edge 不支持它:https://docs.microsoft.com/en-us/internet-explorer/ie11-deploy-guide/deprecated-document-modes
<?xml version='1.0' encoding='ISO-8859-1'?>
<?xml-stylesheet type='text/xsl' href='IndexLog.xsl'?>
<!DOCTYPE myRoot [<!ENTITY thisMonthLog SYSTEM "current.log">]>
<myRoot>
&thisMonthLog;
</myRoot>
日志 current.log 看起来像这样:
<block>
<a>any text</a>
<b>any text</b>
<c>any text</c>
<d>any text</d>
<e>any text</e>
</block>
<block>
<a>any text</a>
<b>any text</b>
<c>any text</c>
<d>any text</d>
<e>any text</e>
</block>
根据您的意见,我了解到您直接使用 IE 11 从文件系统加载 XML 文档。我认为 IE 已转而使用 MSXML 6 而不是 MSXML 3 默认用于 XSLT 和 MSXML 6 默认禁止 DTD 并且不加载外部实体。我知道绕过它的唯一方法是将 MSXML 6 与脚本一起使用并设置它必须允许 DTD 的属性,加载外部资源(对于您的情况,因为 DTD 仅用于加载外部资源实体,禁用验证):
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
version="1.0">
<xsl:output method="html" indent="yes" version="5" doctype-system="about:legacy-doctype"/>
<xsl:template match="/">
<html>
<head>
<title>Test</title>
<script>
function runXslt(xmlUri, xsltUri, targetElement) {
var xmlDoc = new ActiveXObject('Msxml2.DOMDocument.6.0');
xmlDoc.async = false;
xmlDoc.resolveExternals = true;
xmlDoc.validateOnParse = false;
xmlDoc.setProperty('ProhibitDTD', false);
xmlDoc.load(xmlUri);
var xsltDoc = new ActiveXObject('Msxml2.DOMDocument.6.0');
xsltDoc.async = false;
xsltDoc.load(xsltUri);
targetElement.insertAdjacentHTML('beforeEnd', xmlDoc.documentElement.transformNode(xsltDoc));
}
</script>
<script>
document.addEventListener(
'DOMContentLoaded',
function() {
runXslt('test201706070101.xml', 'test2017060701.xsl', document.body);
},
false
);
</script>
</head>
<body>
<h1>Test</h1>
</body>
</html>
</xsl:template>
<xsl:template match="myRoot">
<section>
<h2>Content</h2>
<xsl:apply-templates/>
</section>
</xsl:template>
<xsl:template match="block">
<ul>
<xsl:apply-templates/>
</ul>
</xsl:template>
<xsl:template match="block/*">
<li>
<xsl:apply-templates/>
</li>
</xsl:template>
</xsl:stylesheet>
这样的话,如果输入文档test201706070101.xml
的内容是
<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/xsl" href="test2017060701.xsl"?>
<!DOCTYPE myRoot [
<!ENTITY thisMonthLog SYSTEM "test201706070102.xml">
]>
<myRoot>
&thisMonthLog;
</myRoot>
在 IE 11 中加载并启用脚本,解析完整日志,例如第二个文件有
<?xml version="1.0" encoding="UTF-8"?>
<block>
<a>any text</a>
<b>any text</b>
<c>any text</c>
<d>any text</d>
<e>any text</e>
</block>
<block>
<a>any text</a>
<b>any text</b>
<c>any text</c>
<d>any text</d>
<e>any text</e>
</block>
并且样式表已经post编辑,IE window 中的输出是
Test
Content
•any text
•any text
•any text
•any text
•any text
•any text
•any text
•any text
•any text
•any text
所以外部实体已经加载。主要缺点显然是需要脚本,另一个缺点是使用的带有 MSXML 和 ActiveXObject 的脚本与 Edge 不兼容,因为它不支持 ActiveXObject.
我 post 这个答案是关于如果您想依靠 IE 进行 XSLT 转换可能有帮助的建议,从长远来看,将 XSLT 移动到 HTML 转换可能会更好到 .NET 这样的平台,您可以在其中更好地控制 XML 解析和 XSLT 处理的交互方式。
示例文件在 https://martin-honnen.github.io/xslt/2017/test201706070101.xml, https://martin-honnen.github.io/xslt/2017/test201706070102.xml and https://martin-honnen.github.io/xslt/2017/test2017060701.xsl 上在线,但我知道您想在本地而不是通过 HTTP(S) 执行此操作。