无法遍历FOR XML AUTO结果

时间:2012-12-31 07:10:50

标签: sql-server xml xslt xslt-1.0

我通过存储过程从DB获取一些数据,我使用FOR XML AUTO来获取这些数据。 查询就像这样

WHERE ITEMNUMBER=@itemid AND DATASET = @dataset FOR XML AUTO, ELEMENTS) AS filters

,结果xml是

    <filters extra="filters">
    <ISP_WebItem>
      <FILTER>Type</FILTER>
      <FILTERNAME>Matematik</FILTERNAME>
      <UNITCODE></UNITCODE>
    </ISP_WebItem>
    <ISP_WebItem>
      <FILTER>Strømkilde</FILTER>
      <FILTERNAME>Solceller</FILTERNAME>
      <UNITCODE></UNITCODE>
    </ISP_WebItem>
  </filters>

现在我的问题是,当我尝试在我的xslt中循环遍历此结果时,我无法获得任何结果。 我的XSLT代码就像这样

  <xsl:variable name="filt" select="msxsl:node-set(filters)"/>   
<xsl:for-each select="$filt/ISP_WebItem">   
  <xsl:copy-of select="FILTER"/>
</xsl:for-each>

我正在我的过滤器中正确地获取过滤器xml。变量,但每个循环永远不会正确执行。 当我尝试在我的代码中添加断点时,我注意到代码执行永远不会进入循环内部,这意味着

 <xsl:for-each select="filt/ISP_WebItem">   

这段代码永远不会满足。 有关额外信息,此过滤器节点是大型XML数据的一部分,此数据中的每个其他节点都正常工作(即我可以循环或对它们执行任何操作)。 可以任何人提出任何可能的原因。

1 个答案:

答案 0 :(得分:2)

您的XSLT存在两个问题。首先, filt 是一个变量,所以你需要在它前面添加一个$来表示这个,否则XSLT将寻找一个名为 filt 的元素

<xsl:for-each select="$filt/ISP_WebItem">   

其次,在您的XML示例中, FILTER 是一个元素,但您的 xsl:copy-of 语句正在查找名为“FILTER”的属性。你应该这样做

<xsl:copy-of select="FILTER"/>

但是,如果是属性,请将其保留为<xsl:copy-of select="@FILTER"/>

这个XSLT可以工作,例如

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:msxsl="urn:schemas-microsoft-com:xslt" extension-element-prefixes="msxsl">
   <xsl:output method="xml" indent="yes"/>
   <xsl:template match="/">
      <xsl:variable name="filt" select="msxsl:node-set(filters)"/>
      <xsl:for-each select="$filt/ISP_WebItem">
         <xsl:copy-of select="FILTER"/>
      </xsl:for-each>
   </xsl:template>
</xsl:stylesheet>

事实上,如果您只想复制元素,而不是其他内容,则可以删除 xsl:for-each 并将其简化为此

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:msxsl="urn:schemas-microsoft-com:xslt" extension-element-prefixes="msxsl">
   <xsl:output method="xml" indent="yes"/>
   <xsl:template match="/">
      <xsl:variable name="filt" select="filters"/>
      <xsl:copy-of select="$filt/ISP_WebItem/FILTER"/>
   </xsl:template>
</xsl:stylesheet>

但是,我不太确定你是否需要在这个实例中使用 node-set (虽然我猜你只是展示一个被驱动的代码示例,所以也许有必要在其他地方使用)

以下也适用

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:msxsl="urn:schemas-microsoft-com:xslt" extension-element-prefixes="msxsl">
   <xsl:output method="xml" indent="yes"/>
   <xsl:template match="/">
      <xsl:for-each select="filters/ISP_WebItem">
         <xsl:copy-of select="FILTER"/>
      </xsl:for-each>
   </xsl:template>
</xsl:stylesheet>

编辑:如果您仍然遇到问题,请尝试以下其中一项尝试。

<xsl:for-each select="$filt//ISP_WebItem">