You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在XSL中按序列顺序拼接消息?附XML示例需求

在XSL中按指定顺序拼接GiftMessage并填入CommentText节点

我来帮你搞定这个需求~咱们先明确目标:把属于同一个GiftWrapId和ClientIItemId的GiftMessage内容,按照GiftMessageSequence的数字顺序拼接成一个完整字符串,再把结果放到指定的CommentText节点里。

先看你的输入XML:

<Gifts>
    <Gift>
        <GiftWrapId>026272275</GiftWrapId>
        <ClientIItemId>191267166704</ClientIItemId>
        <GiftMessageSequence>1</GiftMessageSequence>
        <GiftMessageType>GIFT</GiftMessageType>
        <GiftMessage>Happy Birthday, sweet</GiftMessage>
    </Gift>
    <Gift>
        <GiftWrapId>026272275</GiftWrapId>
        <ClientIItemId>191267166704</ClientIItemId>
        <GiftMessageSequence>2</GiftMessageSequence>
        <GiftMessageType>GIFT</GiftMessageType>
        <GiftMessage>Konnie</GiftMessage>
    </Gift>
</Gifts>

期望输出:

<CommentInfo>
    <CommentType>X</CommentType>
    <CommentText>Happy Birthday, sweet Konnie</CommentText>
</CommentInfo>

解决方案(分XSLT版本)

1. XSLT 1.0 兼容版(适合大多数环境)

这个版本用分组键和排序来实现,兼容性拉满:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
    <xsl:output method="xml" indent="yes"/>

    <!-- 用GiftWrapId+ClientIItemId拼接作为分组键,避免单一ID重复 -->
    <xsl:key name="giftGroup" match="Gift" use="concat(GiftWrapId, '|', ClientIItemId)"/>

    <xsl:template match="/">
        <CommentInfo>
            <CommentType>X</CommentType>
            <CommentText>
                <!-- 取出当前分组的所有Gift节点,按Sequence数字排序 -->
                <xsl:for-each select="key('giftGroup', concat(Gift[1]/GiftWrapId, '|', Gift[1]/ClientIItemId))">
                    <xsl:sort select="GiftMessageSequence" data-type="number"/>
                    <!-- 输出当前GiftMessage内容 -->
                    <xsl:value-of select="GiftMessage"/>
                    <!-- 最后一个节点后不加空格 -->
                    <xsl:if test="position() != last()">
                        <xsl:text> </xsl:text>
                    </xsl:if>
                </xsl:for-each>
            </CommentText>
        </CommentInfo>
    </xsl:template>
</xsl:stylesheet>

2. XSLT 2.0+ 简洁版

如果你的环境支持XSLT 2.0或更高版本,可以用更简洁的写法,利用内置的排序和分隔符属性:

<xsl:stylesheet version="2.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
    <xsl:output method="xml" indent="yes"/>

    <xsl:template match="/">
        <CommentInfo>
            <CommentType>X</CommentType>
            <CommentText>
                <!-- 筛选同组节点 → 按Sequence排序 → 提取GiftMessage并指定空格分隔 -->
                <xsl:value-of select="
                    Gift[concat(GiftWrapId, '|', ClientIItemId) = concat(/Gift[1]/GiftWrapId, '|', /Gift[1]/ClientIItemId)]
                    /sort((.), function($g) {number($g/GiftMessageSequence)})
                    /GiftMessage" 
                separator=" "/>
            </CommentText>
        </CommentInfo>
    </xsl:template>
</xsl:stylesheet>

关键细节说明

  • 分组逻辑:用concat(GiftWrapId, '|', ClientIItemId)作为分组键,确保只有同时匹配两个ID的节点才会被分到同一组,避免单一ID重复导致的错误分组。
  • 排序注意:一定要给xsl:sort加上data-type="number"(XSLT1.0)或用number()转换(XSLT2.0+),不然会按字符串排序(比如数字10会排在2前面)。
  • 空格处理:XSLT1.0里通过position() != last()判断,避免末尾多出来的空格;XSLT2.0+直接用separator=" "就能自动处理分隔,更省心。

内容的提问来源于stack exchange,提问作者Aswin Francis

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.15 07:16:52