如何在处理指令中查找更新日期 - XSLT

How to find updated date in processing instruction - XSLT

如果在 p 元素中找到处理指令并创建值 updated date.
,我将尝试在 p 元素中创建属性 lastUpdatedOn 输入XML

<root>
    <p content-type="new">Ongoing technological and <?lastUpdatedOn 20/01/2021?>privacy developments present practicing <?lastUpdatedOn 27/01/2021?>attorneys with significant challenges in the field of information privacy and <?lastUpdatedOn 25/01/2020?>security.</p>
    <p content-type="new">Developments present <?lastUpdatedOn 26/01/2021?>practicing.</p>
    <p content-type="new">Practicing the Labs.</p>
</root>

预期输出

<root>
    <p content-type="new" lastupdatedon="27/01/2021">Ongoing technological and <?lastUpdatedOn 20/01/2021?>privacy developments present practicing <?lastUpdatedOn 27/01/2021?>attorneys with significant challenges in the field of information privacy and <?lastUpdatedOn 25/01/2020?>security.</p>
    <p content-type="new" lastupdatedon="26/01/2021">Developments present <?lastUpdatedOn 26/01/2021?>practicing.</p>
    <p content-type="new">Practicing the Labs.</p>
</root>

XSLT 代码

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

<xsl:template match="p">
    <xsl:copy>
        <xsl:copy-of select="@*"/>
        <xsl:if test="processing-instruction(lastUpdatedOn)">
            <xsl:attribute name="lastupdatedon">
                <xsl:value-of select="processing-instruction(lastUpdatedOn)"/>
            </xsl:attribute>
        </xsl:if>
        <xsl:apply-templates/>
    </xsl:copy>
</xsl:template>

正确的模式或测试是 processing-instruction('lastUpdatedOn')。我会把它塞进 p 的匹配中,例如

<xsl:template match="p[processing-instruction('lastUpdatedOn')]">
  <xsl:copy>
     <xsl:apply-templates select="@*, processing-instruction('lastUpdatedOn'), node() except processing-instruction('lastUpdatedOn')"/>
  </xsl:copy>
</xsl:template>

<xsl:template match="processing-instruction('lastUpdatedOn')">
   <xsl:attribute select="{name()}" select="."/>
</xsl:template>

其余的可以通过身份转换处理,例如<xsl:mode on-no-match="shallow-copy"/>.

因为你似乎有多个处理指令用

对它们进行排序
<xsl:template match="p[processing-instruction('lastUpdatedOn')]">
  <xsl:copy>
     <xsl:apply-templates select="@*, sort(processing-instruction('lastUpdatedOn'), (), function($p) { xs:date(replace($p, '([0-9]{2})/([0-9]{2})/([0-9]{4})', '--')) })[last()], node() except processing-instruction('lastUpdatedOn')"/>
  </xsl:copy>
</xsl:template>

<xsl:template match="processing-instruction('lastUpdatedOn')">
   <xsl:attribute name="lastupdatedon" select="."/>
</xsl:template>

有助于仅显示最后日期。高阶 fn:sort 在 Saxon PE 和 EE 中至少从 9.8 开始可用,在 Saxon HE 中可用于 10 及更高版本。

上面会将日期移动到属性,但会从 p 中删除处理指令,如果您可能需要保留它们

  <xsl:template match="p[processing-instruction('lastUpdatedOn')]">
    <xsl:copy>
       <xsl:apply-templates select="@*, sort(processing-instruction('lastUpdatedOn')!xs:date(replace(., '([0-9]{2})/([0-9]{2})/([0-9]{4})', '--')))[last()], node()"/>
    </xsl:copy>
  </xsl:template>
  
  <xsl:template match=".[. instance of xs:date]">
     <xsl:attribute name="lastupdatedon" select="."/>
  </xsl:template>

是更好的方法。