在同一 uri 中更新多个结果

update more than one result in same uri

我想更新相同的结果文档以累积所有元元素。我试图重新创建多个 dita-ot 模板来解释这里的问题。我的问题是,是否可以在

中更新 keyword.xml
<xsl:template match="html" mode="pages"> 

模板本身?也许使用 xsl:stream 或 xsl:accumulator? XSLT 3 和 Saxon-HE-9.8.0-12

输入XML

<root>
<article>
<html name="firsthtm">
    <head>Head1</head>
    <meta>keyword;firsthtm</meta>
</html>
<html name="secondhtm">
    <head>Head2</head>
    <meta>keyword;secondhtm</meta>
</html>
<html name="thirdhtm">
    <head>Head3</head>
    <meta>keyword;thirdhtm</meta>
</html>
</article>

XSLT

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:xs="http://www.w3.org/2001/XMLSchema" exclude-result-prefixes="xs" version="3.0">
<xsl:template match="/">
    <xsl:apply-templates/>
</xsl:template>
<xsl:template match="article">
    <xsl:apply-templates mode="pages"/>
</xsl:template>
<xsl:template match="html" mode="pages">
    <xsl:result-document href="{@name}.html">
        <html>
            <title>
                <xsl:value-of select="@name"/>
            </title>
        </html>
    </xsl:result-document>
    <!-- update keyword.xml for each html  -->
    <xsl:result-document href="keyword.xml">
        <root>
            <xsl:copy-of select="meta"/>
        </root>      
    </xsl:result-document>
</xsl:template>

 firsthtm.htm
 <html>
     <title>firsthtm</title>
 </html>

 secondhtm.htm
 <html>
     <title>secondhtm</title>
 </html>

 thirdhtm.htm
 <html>
     <title>thirdhtm</title>
 </html>

 keyword.xml
 <root>
     <meta>keyword;secondhtm</meta>
     <meta>keyword;secondhtm</meta>
     <meta>keyword;thridhtm</meta>
 </root>

只需在匹配article:

的模板中创建结果文档
<xsl:template match="article">
    <xsl:apply-templates mode="pages"/>
    <xsl:result-document href="keyword.xml">
        <root>
            <xsl:copy-of select="html/meta"/>
        </root>      
    </xsl:result-document>
</xsl:template>

如果你想使用 match="html" mode="pages" 那么你必须决定你想要构造那个结果的匹配,例如在第一个

<xsl:template match="html" mode="pages">
    <xsl:result-document href="{@name}.html">
        <html>
            <title>
                <xsl:value-of select="@name"/>
            </title>
        </html>
    </xsl:result-document>
    <!-- update keyword.xml for first html  -->
    <xsl:variable name="html-index" as="xs:integer">
      <xsl:number/>
    </xsl:variable>
    <xsl:if test="$html-index = 1">
      <xsl:result-document href="keyword.xml">
        <root>
            <xsl:copy-of select="ancestor::article/html/meta"/>
        </root>      
      </xsl:result-document>
    </xsl:if>
</xsl:template>

在简单的情况下(article 只有那些 html 个子元素,而您已经使用了 xsl:strip-space),简单地测试 <xsl:if test="position() = 1"> 可能就足够了。

一个简单的解决方案是将 xsl:result-document 移动到 article 模板并从那里复制所有 html/meta 元素:

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:xs="http://www.w3.org/2001/XMLSchema" exclude-result-prefixes="xs" version="3.0">

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

    <xsl:template match="article">
        <xsl:apply-templates mode="pages"/>
        <xsl:result-document href="keyword.xml">
            <root>
                <xsl:copy-of select="html/meta"/>
            </root>            
        </xsl:result-document>
    </xsl:template>

    <xsl:template match="html" mode="pages">
        <xsl:result-document href="{@name}.html">
            <html>
                <title>
                    <xsl:value-of select="@name"/>
                </title>
            </html>
        </xsl:result-document>
        <!-- update keyword.xml for each html  -->
    </xsl:template>

</xsl:stylesheet>