XPATH没有检索节点II

时间:2013-08-04 00:00:47

标签: xml xslt aspxgridview xpath-2.0

我正在学习XPath,在练习w /我在网上找到的xml文件时,应用程序在将XSL文件实现到项目后无法呈现任何值。我非常感谢任何关于我遗失或做错的建议。

XML文件:

<?xml version="1.0" encoding="utf-8"?>
<root>
    <Customers>
        <Customer>
            <Id>1</Id>
            <FirstName>Joe</FirstName>
            <Surname>Doe</Surname>
        </Customer>
   </Customers>
    <Customers>
          <Customer>
            <Id>2</Id>
            <FirstName>Mary</FirstName>
            <Surname>Brown</Surname>
        </Customer>
    </Customers>
    <Customers>
        <Customer>
            <Id>3</Id>
            <FirstName>Paul</FirstName>
            <Surname>Smith</Surname>
        </Customer>
    </Customers>
    </root>

XSL:

<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:msxsl="urn:schemas-microsoft-com:xslt" exclude-result-prefixes="msxsl">
    <xsl:template match ="/">
        <root>
            <xsl:apply-templates select ="//Customers"/>
        </root>
    </xsl:template>
    <xsl:template match ="//Customer">
        <Customer>
            <xsl:attribute name="Id">
                <xsl:value-of select="Id"/>
            </xsl:attribute>
            <xsl:attribute name="FirstName">
                <xsl:value-of select="FirstName"/>
            </xsl:attribute>
            <xsl:attribute name="Surname">
                <xsl:value-of select="Surname"/>
            </xsl:attribute>
        </Customer>
    </xsl:template>
</xsl:stylesheet>

ASPX:

<asp:XmlDataSource ID="XmlDataSource1" runat="server" 
            DataFile="~/xml/Sample-no-attributes.xml" 
            TransformFile="~/xml/Sample-no-attributes.xsl"
            XPath="/root/Customers">
      </asp:XmlDataSource>

        <asp:GridView ID="GridView1" runat="server" AutoGenerateColumns="False" 
            DataSourceID="XmlDataSource1">
            <Columns>
                 <asp:TemplateField HeaderText="CustomerID">
            <ItemTemplate>
                <%# XPath("Customer/Id")%>
             </ItemTemplate>
            </asp:TemplateField>

            <asp:TemplateField HeaderText="First Name">
            <ItemTemplate>
                <%# XPath("Customer/FirstName")%>
             </ItemTemplate>
            </asp:TemplateField>

             <asp:TemplateField HeaderText="Surname">
            <ItemTemplate>
                <%# XPath("Customer/Surname")%>
             </ItemTemplate>
            </asp:TemplateField>
            </Columns>
        </asp:GridView>

请提供一些帮助,说明我在这里做错了什么。

1 个答案:

答案 0 :(得分:1)

测试你的XSLT显示输出XML如下:

<root>
    <Customer Id="1" FirstName="Joe" Surname="Doe"/>
    <Customer Id="2" FirstName="Mary" Surname="Brown"/>
    <Customer Id="3" FirstName="Paul" Surname="Smith"/>
</root>

如果您注意到,此处不会出现 Customers 元素,但asp:XmlDataSource中的XPath表达式为“/ root / Customers”。

假设您确实要删除 Customers 元素,首先需要相应地更改Xpath表达式

XPath="/root/Customer"

但是您的项目模板中的XPath表达式也存在问题

    <ItemTemplate>
        <%# XPath("Customer/Id")%>
    </ItemTemplate>

使用当前修复程序,您需要从表达式中删除客户,因为您现在可以定位在客户元素上。但是,在输出XML中, Id 现在是属性,而不是子元素。这意味着你的Xpath必须是这样的(注意用于属性的@符号)

    <ItemTemplate>
        <%# XPath("@Id")%>
    </ItemTemplate>

试试这个ASPX

 <asp:XmlDataSource ID="XmlDataSource1" runat="server" 
        DataFile="~/Sample-no-attributes.xml" 
        TransformFile="~/Sample-no-attributes.xsl"
        XPath="/root/Customer">
  </asp:XmlDataSource>

    <asp:GridView ID="GridView1" runat="server" AutoGenerateColumns="False" 
        DataSourceID="XmlDataSource1">
        <Columns>
             <asp:TemplateField HeaderText="CustomerID">
        <ItemTemplate>
            <%# XPath("@Id")%>
         </ItemTemplate>
        </asp:TemplateField>

        <asp:TemplateField HeaderText="First Name">
        <ItemTemplate>
            <%# XPath("@FirstName")%>
         </ItemTemplate>
        </asp:TemplateField>

         <asp:TemplateField HeaderText="Surname">
        <ItemTemplate>
            <%# XPath("@Surname")%>
         </ItemTemplate>
        </asp:TemplateField>
        </Columns>
    </asp:GridView>

请注意,如果您确实希望在XSLT中保留客户,则可能值得理解他们失踪的原因。在您的第一个模板中,您可以执行此操作

<xsl:apply-templates select ="//Customers"/>

但您的XSLT中没有匹配客户的模板。发生这种情况时,XSLT的内置模板适用。这些输出元素中的任何文本节点,然后查找与其子元素匹配的模板。但它不会输出元素本身。因此,您将失去客户元素。

要保留它,您可以添加以下模板

 <xsl:template match ="Customers">
    <Customers>
      <xsl:apply-templates select ="Customer"/>
    </Customers>
 </xsl:template>

但是,最好在此处使用XSLT Identity Transform复制现有元素。

试试这个XLST,它会保留客户元素。请注意,您不需要显式模板来匹配 Root Customers 。另请注意使用属性值模板输出每个 Customer 元素的属性,使代码更简洁。

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:msxsl="urn:schemas-microsoft-com:xslt" exclude-result-prefixes="msxsl">

  <xsl:template match="@*|node()">
    <xsl:copy>
      <xsl:apply-templates select="@*|node()"/>
    </xsl:copy>
  </xsl:template>

  <xsl:template match ="//Customer">
    <Customer Id="{Id}" FirstName="{FirstName}" Surname="{Surname}" />
  </xsl:template>
</xsl:stylesheet>

如果您使用此XSLT,则asp:XmlDataSource的XPath将保留为“/ root / Customers”,但ItemTemplates的XPath将为<%# XPath("Customer/@Id")%>