2016-11-24 50 views
0

输入XML的XML:排序使用XSLT

<soap-env:Envelope xmlns:soap-env="http://schemas.xmlsoap.org/soap/envelope/"> 
    <soap-env:Header> 
     <wsse:Security xmlns:wsse="http://schemas.xmlsoap.org/ws/2002/12/secext"> 
      <wsse:Username>User</wsse:Username> 
      <wsse:Password>Password</wsse:Password> 
     </wsse:Security> 
    </soap-env:Header> 
    <soap-env:Body> 
     <soap-env:CustomerRs> 
      <Information> 
       <Identity Code="DFW"> 
        <User LoginID="123456" /> 
       </Identity> 
       <User> 
        <Customer Gender="Male"> 
         <Person> 
          <GivenName>Tester2</GivenName> 
          <LastName>Tester</LastName> 
         </Person> 
         <Telephone Type="Business" InfoNo="1" SeqNo="1"> 
          <Number Area="456" Phone="7878787" /> 
         </Telephone> 
         <Info InfoNo="2" SeqNo="1"> 
          <LastName>Wilson</LastName> 
          <GivenName>Kelley</GivenName> 
         </Info> 
         <Info InfoNo="4" SeqNo="1"> 
          <LastName>Graham</LastName> 
          <GivenName>Tom</GivenName> 
         </Info> 
         <Info InfoNo="1" SeqNo="3"> 
          <LastName>Fisher</LastName> 
          <GivenName>Elaine</GivenName> 
         </Info> 
         <Info InfoNo="1" SeqNo="2"> 
          <LastName>Gary</LastName> 
          <GivenName>Jerry</GivenName> 
         </Info> 
         <Info InfoNo="1" SeqNo="1"> 
          <LastName>Timothy</LastName> 
          <GivenName>Kathy</GivenName> 
         </Info> 
         <Info InfoNo="3" SeqNo="1"> 
          <LastName>Tim</LastName> 
          <GivenName>Kerry</GivenName> 
         </Info> 
         <Info InfoNo="1" SeqNo="4"> 
          <LastName>Rob</LastName> 
          <GivenName>Tony</GivenName> 
         </Info> 
         <Address Type="Business" InfoNo="1" SeqNo="1"> 
          <Line1>Menands Ln</Line1> 
          <City>Albany</City> 
         </Address> 
        </Customer> 
        <Order type="S"> 
         <Ref>ABC123</Ref> 
         <OrderedBy> 
          <Debtor code="BLABLA"></Debtor> 
         </OrderedBy> 
         <DeliveryMethod code="Barefoot"></DeliveryMethod> 
         <OrderLine line="1"> 
          <Item code="QQQ123456"></Item> 
          <Quantity>1</Quantity> 
         </OrderLine> 
        </Order> 
       </User> 
      </Information> 
     </soap-env:CustomerRs> 
    </soap-env:Body> 
</soap-env:Envelope> 

期望输出XML响应:

<soap-env:Envelope xmlns:soap-env="http://schemas.xmlsoap.org/soap/envelope/"> 
    <soap-env:Header> 
     <wsse:Security xmlns:wsse="http://schemas.xmlsoap.org/ws/2002/12/secext"> 
      <wsse:Username>User</wsse:Username> 
      <wsse:Password>Password</wsse:Password> 
     </wsse:Security> 
    </soap-env:Header> 
    <soap-env:Body> 
     <soap-env:CustomerRs> 
      <Information> 
       <Identity Code="DFW"> 
        <User LoginID="123456" /> 
       </Identity> 
       <User> 
        <Customer Gender="Male"> 
         <Person> 
          <GivenName>Tester2</GivenName> 
          <LastName>Tester</LastName> 
         </Person> 
         <Telephone Type="Business" InfoNo="1" SeqNo="1"> 
          <Number Area="456" Phone="7878787" /> 
         </Telephone> 
         <Info InfoNo="1" SeqNo="1"> 
          <LastName>Timothy</LastName> 
          <GivenName>Kathy</GivenName> 
         </Info> 
         <Info InfoNo="1" SeqNo="2"> 
          <LastName>Gary</LastName> 
          <GivenName>Jerry</GivenName> 
         </Info> 
         <Info InfoNo="1" SeqNo="3"> 
          <LastName>Fisher</LastName> 
          <GivenName>Elaine</GivenName> 
         </Info> 
         <Info InfoNo="1" SeqNo="4"> 
          <LastName>Rob</LastName> 
          <GivenName>Tony</GivenName> 
         </Info> 
         <Info InfoNo="2" SeqNo="1"> 
          <LastName>Wilson</LastName> 
          <GivenName>Kelley</GivenName> 
         </Info> 
         <Info InfoNo="3" SeqNo="1"> 
          <LastName>Tim</LastName> 
          <GivenName>Kerry</GivenName> 
         </Info> 
         <Info InfoNo="4" SeqNo="1"> 
          <LastName>Graham</LastName> 
          <GivenName>Tom</GivenName> 
         </Info> 
         <Address Type="Business" InfoNo="1" SeqNo="1"> 
          <Line1>Menands Ln</Line1> 
          <City>Albany</City> 
         </Address> 
        </Customer> 
        <Order type="S"> 
         <Ref>ABC123</Ref> 
         <OrderedBy> 
          <Debtor code="BLABLA"></Debtor> 
         </OrderedBy> 
         <DeliveryMethod code="Barefoot"></DeliveryMethod> 
         <OrderLine line="1"> 
          <Item code="QQQ123456"></Item> 
          <Quantity>1</Quantity> 
         </OrderLine> 
        </Order> 
       </User> 
      </Information> 
     </soap-env:CustomerRs> 
    </soap-env:Body> 
</soap-env:Envelope> 

我的XSLT是做转型:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> 
    <xsl:output omit-xml-declaration="yes" indent="yes" /> 
    <xsl:template match="node()|@*"> 
     <xsl:copy> 
      <xsl:apply-templates select="node()|@*" /> 
     </xsl:copy> 
    </xsl:template> 
    <xsl:template match="/*[local-name()='Envelope']"> 
     <xsl:copy> 
      <xsl:apply-templates select="@*|node()"> 
       <xsl:sort select="/*[local-name()='Info']/@*[local-name()='InfoNo']" data-type="number" order="ascending" /> 
       <xsl:sort select="/*[local-name()='Info']/@*[local-name()='SeqNo']" data-type="number" order="ascending" /> 
      </xsl:apply-templates> 
     </xsl:copy> 
    </xsl:template> 
</xsl:stylesheet> 

我用这个样式表进行排序并安排,但仍然生产相同的输入。我做错了什么,我无法得到答复。

回答

1

请考虑以下调整。对于排序,由于您使用标识模板按原样复制文档,因此无需遍历整个树。只需添加一个排序部分的模板,即父标签,这里是<Customer>,然后只排序其<Info>子女。

此外,InfoNo的SeqNo的属性,所以必须用@引用。最后,最佳做法是尝试在XSLT顶部添加<xsl:strip-space elements="*"/>以删除空白文本节点,这样可以增加一点效率,因为这些节点会从内存中分离出来。

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> 
    <xsl:output omit-xml-declaration="yes" indent="yes" /> 
    <xsl:strip-space elements="*"/> 

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

    <xsl:template match="Customer"> 
     <xsl:copy> 
      <xsl:copy-of select="Person|Telephone"/>    
      <xsl:apply-templates select="Info"> 
       <xsl:sort select="@InfoNo" data-type="number" order="ascending" /> 
       <xsl:sort select="@SeqNo" data-type="number" order="ascending" /> 
      </xsl:apply-templates> 
      <xsl:copy-of select="Address"/> 
     </xsl:copy> 
    </xsl:template> 

</xsl:stylesheet> 
0

您需要了解相对路径和绝对路径之间的区别。要计算元素E的排序关键字,您将(几乎)总是要使用从E开始的路径(即相对路径)选择某个值。以“/”开头的路径是绝对路径,它始于文档的顶部,因此计算相同的值,而不管E在哪里。因此,使用绝对路径计算的排序关键字(如<xsl:sort select="/*[.....]"/>)必须是错误的。