如何编辑xsl文件,以便根据一些检查加载不同的模板?

时间:2011-05-13 06:05:13

标签: xml xslt xsl-fo

我有两个xsl文件,每个文件用于不同类型的机器

  1. 用于各种unix香精机
  2. 用于各种Windows机器
  3. 我想基于检查来自这些xsl

    的osname来加载另一个xsl
      

    例如:如果osname =“Windows”,则加载 windows.xsl      否则加载 nix.xsl

    所以为了做到这一点,应该有另一个xsl进行检查。那么现在如何基于osname检查加载这些 windows nix xsl?

    更多细节我正在为win和nix机器提供xml

    1. nix machine xml

      <machine> <system> <osname>Linux</osname> <username>Abhishek</username> </system> </machine>

    2. win machine xml

      <machine> <system> <osinfo> <osinfo field='OS Name' information='Microsoft(R) Windows(R) Server 2003 Enterprise x64 Edition ' /> <osinfo field='OS Version' information='5.2.3790 Service Pack 2 Build 3790 ' /> <osinfo field='OS Manufacturer' information='Microsoft Corporation ' />
      </osinfo> <username>Matt</username> </system> </machine>

    3. 我也提供模板,

        

      unix xsl模板

       <xsl:template name="unixsystem" match="machine">
          <span style="color:#328aa4"><a name="_systeminfo" href="#_top">System Info</a></span>
      
      <table border="1" >
          <tbody>
          <tr>
          <th align="left">OS Name</th>
          <th align="left">User Name</th>
          </tr>
          <tr>
          <td><xsl:value-of select="system/osname"/></td>
          <td><xsl:value-of select="system/username"/></td>
          </tr>
          </tbody>
      </table>
      
          </span>
      </xsl:template>
      
        

      Windows xsl模板

      <xsl:template name="winsystem" match="machine">
              <span style="color:#328aa4"><a name="_ospatches" href="#_top">OS Information: </a></span></h2>
      
              <table border="1">
                  <tbody>
                  <tr>
                      <th>Field</th>
                      <th>Information</th>
                  </tr>
      
                  <xsl:for-each select="osinfo/osinfo">
                      <tr>
                          <td valign="top" ><xsl:value-of select="@field"/></td>
                          <td valign="top" style="width: 2;"><xsl:value-of select="@information"/></td>
                      </tr>
                  </xsl:for-each>
                  </tbody>
              </table>
              </xsl:template>
      

      而不是使用contains这可以吗?

      <xsl:choose>
        <xsl:when test="osinfo/osinfo/@information='Windows'">
          <xsl:call-template name="winsystem"/>
        </xsl:when>
        <xsl:otherwise>
         <xsl:call-template name="unixsystem"/>
        </xsl:otherwise>
      </xsl:choose>
      

2 个答案:

答案 0 :(得分:2)

由于xsl:includexsl:import必须是xsl:stylesheet的孩子,因此您无法有条件地管理它们。

如果您将两个样式表包含在主样式表中,然后根据您的选择调用相应的模板,那可能会更好。

示例:

 <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">

  <xsl:include href="win.xsl"/>
  <xsl:include href="unix.xsl"/>

  <xsl:template match="/">
    <xsl:choose>
      <xsl:when test="contains(//osinfo/@information, 'Windows')">
       <xsl:call-template name="winsystem"/>
      </xsl:when>
      <xsl:otherwise>
       <xsl:call-template name="unixsystem"/>
      </xsl:otherwise>
    </xsl:choose>
  </xsl:template>

 </xsl:stylesheet>

显然,这只是一个建议,它基于两个名为win.xsl和unix.xsl的样式表中名为win和unix的模板。

希望这有帮助


看到模板后的扩展答案

我会以不同的方式命名这两个模板并删除match。我的意思是我会用:

unix xsl

<xsl:template name="unixsystem">
 <!-- your staff -->
</xsl:template>

windows xsl

<xsl:template name="winsystem">
 <!-- your staff -->
</xsl:template>

之后您可以按照上面的说明调用模板。请注意,我已删除match。通过这种方式,您应该能够调用模板。我没有调查你的xsl文件的内容是否正确。我还纠正了我的xsl中的错误代码(未封闭的xsl:choose)。

答案 1 :(得分:1)

通常,如果您需要样式表的两个变体,则应将WIN部分放在WIN.xsl中,LIN部分放在LIN.xsl中,将公共部分放在COMMON.xsl中。然后WIN.xsl应该导入COMMON.xsl; LIN.xsl应该导入COMMON.xsl;如果你想要WIN变种你应该指定WIN.xsl作为你的顶级样式表,而如果你想要LIN变种你应该提名LIN.xsl。

换句话说,特殊情况代码应该导入通用代码,而不是相反。