javascript - Visual Studio 和 IE 之间的 XSL/JScript 行为差异

标签 javascript xml internet-explorer xslt

谁能告诉我为什么下面的 XSL 在 IE9 中愉快地转换了下面的 XML,但同样的转换在所有版本的 Visual Studio 下都失败了?如果我在 IE 9 中打开 XML 文件,它会被转换并且输出符合预期,但如果我尝试在 Visual Studio 中对 XML 文件进行相同的转换(使用工具栏上的“开始 XSLT”按钮),我会得到一个 JScriptException single function expected 就行了

var node = root.nextNode();

解决方法似乎是更改 javascript 函数以改为执行以下操作:

function test(root, attr)
{
  root.MoveNext();
  var node = root.Current;
  return node.Select("breakfast" + attr);
}

但是这会导致 IE 中的 XSLT 转换失败!我好像赢不了!

XSL:

<!--<?xml version="1.0"?>-->
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:msxsl="urn:schemas-microsoft-com:xslt"
xmlns:user="urn:custom-scripts">
<msxsl:script language="JScript" implements-prefix="user">
  <![CDATA[
function test(root, attr)
{
  var node = root.nextNode();
  return node.selectSingleNode("breakfast" + attr);
}
]]>
</msxsl:script>
  <xsl:template match="/">
    <HTML>
      <BODY STYLE="font-family:Arial, helvetica, sans-serif; font-size:12pt;
            background-color:#EEEEEE">
          <xsl:value-of select="user:test(., '-menu')"/>
      </BODY>
    </HTML>
  </xsl:template>
</xsl:stylesheet>

目标 XML:

<?xml version='1.0'?>
<?xml-stylesheet type="text/xsl" href="simple.xsl" ?>
<breakfast-menu>
  <food>
    <name>Belgian Waffles</name>
    <price>$5.95</price>
    <description>Two of our famous Belgian Waffles 
      with plenty of real maple syrup.</description>
    <calories>650</calories>
  </food>
  <food>
    <name>Homestyle Breakfast</name>
    <price>$6.95</price>
    <description>Two eggs, bacon or sausage, toast, 
      and our ever-popular hash browns.</description>
    <calories>950</calories>
  </food>
</breakfast-menu>

最佳答案

嗯,IE 使用 MSXML 作为其 XSLT 处理器(我认为 IE 9 使用 MSXML 6),而 Visual Studio 使用 XslCompiledTransform。 MSXML 和 XslCompiledTransform 公开和使用的 API 差别很大,因此不要指望针对 MSXML API 编写的扩展函数代码可以与 XslCompiledTransform 和 .NET API 一起使用。参见 http://msdn.microsoft.com/en-us/library/wxaw5z5e.aspx关于在使用扩展函数时 XSLT/XPath 类型如何映射到 .NET 类型。在您的情况下,您传入一个节点集和一个来自 XSLT 的字符串,它们映射到 .NET 中的一个 XPathNodeIterator 和一个字符串。 这是为 .NET 重写扩展函数的快速尝试:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:msxsl="urn:schemas-microsoft-com:xslt"
xmlns:user="urn:custom-scripts">
  <msxsl:script language="JScript" implements-prefix="user">
    <![CDATA[
function test(nodeIterator, string)
{
  nodeIterator.MoveNext();
  return nodeIterator.Current.SelectSingleNode("breakfast" + string);
}
]]>
  </msxsl:script>
  <xsl:template match="/">
    <HTML>
      <BODY STYLE="font-family:Arial, helvetica, sans-serif; font-size:12pt;
            background-color:#EEEEEE">
        <xsl:value-of select="user:test(., '-menu')"/>
      </BODY>
    </HTML>
  </xsl:template>
</xsl:stylesheet>

[编辑] 哎呀,我没注意到您已经自己找到了 .NET 代码并且只想知道如何针对两个 XSLT 处理器编写代码。那很难。你的目标平台和目标是什么,你想为 IE 编写 XSLT 而用 VS 开发吗?或者您真的需要在 IE 和 .NET 平台上使用相同的样式表吗?

这里尝试为两种类型的处理器编写一个扩展函数:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:msxsl="urn:schemas-microsoft-com:xslt"
xmlns:user="urn:custom-scripts">
  <msxsl:script language="JScript" implements-prefix="user">
    <![CDATA[
function test(nodeSet, string)
{
  if (typeof nodeSet.nextNode !== 'undefined') {
    var node = nodeSet.nextNode();
    return node.selectSingleNode('breakfast' + string);
  }
  else if (typeof nodeSet.MoveNext !== 'undefined') {
    nodeSet.MoveNext();
    return nodeSet.Current.SelectSingleNode("breakfast" + string);
  }
}
]]>
  </msxsl:script>
  <xsl:template match="/">
    <HTML>
      <BODY STYLE="font-family:Arial, helvetica, sans-serif; font-size:12pt;
            background-color:#EEEEEE">
        <xsl:value-of select="user:test(., '-menu')"/>
      </BODY>
    </HTML>
  </xsl:template>
</xsl:stylesheet>

关于javascript - Visual Studio 和 IE 之间的 XSL/JScript 行为差异,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6095635/

相关文章:

德尔福。如何监控 IE 正在下载的 URL?

internet-explorer - 在 IE 中使用 AlphaImageLoader 过滤器时隐藏标准背景

javascript - Angular 4导入isPropertyUpdated方法

javascript - 带有表单条件的 ng-show 不适用于 AngularJS 中的指令模板

javascript - 我正在尝试使用复选框作为条件

java - 如何从 XML 文件中读取数据并将其存储到数据库 (MySQL)?

json - 当 Angulars $http.post 与大型/复杂 json 数据集一起使用时,Internet Explorer 11 崩溃

javascript - nunjucks 函数参数未定义

从 MySQL Workbench 导出 EER 图的 XML

xml - 获取 cordova 的 config.xml 的 XPath