XML到HTML(XSLT):复制替换某些行并添加新行的节点

时间:2011-10-31 10:28:19

标签: html xml xslt svg

我必须将<script>节点从xml复制到html,但我需要在其中替换它的某些行,并添加新的节点。所以我需要在整个节点复制时搜索和替换字符串。

XML示例:

<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink"
id="slot" width="320" height="245">

   <script type="application/javascript"><![CDATA[
      var a = 2;
      var b = "abc";
      var c = new Array(0,0,0);
      alert("Input!");
   ]]></script>

   <!-- here svg drawing tags -->

</svg>

HTML输出示例:

<html>
   <head>
      <title>Example!</title>

      <script type="application/javascript">
          var a = 2;                          <!---same as xml--->
          var b = "def";                      <!---modified--->
          var c = new Array(0,0,0);           <!---same as xml---> 
          alert("This is a new example!");    <!---modified---> 
          var new = "new var";                <!---new code--->             
      </script>
   </head> 
   <body>
   </body>
</html>

如果这很容易,我可以使用XTLS 2.0。 我该怎么办?

1 个答案:

答案 0 :(得分:1)

此转化

<xsl:stylesheet version="2.0"
        xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
        xmlns:xs="http://www.w3.org/2001/XMLSchema"
        xmlns:svg="http://www.w3.org/2000/svg"
        xmlns:my="my:my">
        <xsl:output omit-xml-declaration="yes" indent="yes"/>

        <xsl:param name="pSrcEdits">
         <line num="2" act="del"/>
         <line num="4" act="rep"
               newLine="var c = new Array(1,1,1);"/>
         <line num="5" act="ins"
               newLine="/* Inserted comment */"/>
        </xsl:param>

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

 <xsl:template match="svg:script/text()">
  <xsl:variable name="vLines" select="tokenize(., '&#xD;?&#xA;')"/>

  <xsl:sequence select="my:editLines($vLines, $pSrcEdits/*)"/>
 </xsl:template>

 <xsl:function name="my:editLines" as="xs:string*">
  <xsl:param name="pLines" as="xs:string*"/>
  <xsl:param name="pCommands" as="element()*"/>

  <xsl:for-each select="$pLines">
   <xsl:variable name="vLineNum" as="xs:integer"
    select="position()"/>
   <xsl:variable name="vCommand"
     select="$pCommands[number(@num) eq  $vLineNum]"/>
   <xsl:sequence select="my:editSingle(., $vCommand)"/>
  </xsl:for-each>
 </xsl:function>

 <xsl:function name="my:editSingle" as="xs:string?">
  <xsl:param name="pLine" as="xs:string"/>
  <xsl:param name="pCommand" as="element()?"/>

  <xsl:sequence select=
  "if(not($pCommand))
     then concat($pLine, '&#xA;')
     else
      if($pCommand/@act eq 'del')
         then ()
         else
          if($pCommand/@act eq 'rep')
            then concat($pCommand/@newLine, '&#xA;')
            else (: 'ins' :)
              concat($pCommand/@newLine, '&#xA;', $pLine, '&#xA;')
  "/>

 </xsl:function>
</xsl:stylesheet>

应用于提供的XML文档

<svg xmlns="http://www.w3.org/2000/svg"
xmlns:xlink="http://www.w3.org/1999/xlink"
id="slot" width="320" height="245">

   <script type="application/javascript"><![CDATA[
      var a = 2;
      var b = "abc";
      var c = new Array(0,0,0);
      alert("Input!");
   ]]></script>

   <!-- here svg drawing tags -->

</svg>

生成想要的结果(执行所有命令并编辑脚本):

<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink"
     id="slot"
     width="320"
     height="245">

   <script type="application/javascript">
       var b = "abc";
 var c = new Array(1,1,1);
 /* Inserted comment */
      alert("Input!");

</script>

   <!-- here svg drawing tags -->

</svg>