XSLT 1.0 - 如何将 2 elements/siblings 合并为 1 组

XSLT 1.0 - How to combine 2 elements/siblings into 1 group

我希望我没有毁掉这个标题。

我是 XML 和 XSLT 转换的初学者,经过几天的研究和一些认真的试验和错误,我走到了这一步,但现在我绝望了。我似乎无法找到组合 customer_ids 的方法,因为它们可以来自 2 个不同的元素并且结果必须具有唯一性 customer_ids.

我该如何继续?

这里是源代码示例XML,我需要转换。

<result>
<row>
    <string>HR-039780</string>
    <string>PER-013</string>
    <null/>
    <string>HelpRequest</string>
    <string>CID-009</string>
    <string>SP-004</string>
    <string>SG-002</string>
</row>
<row>
    <string>SR-003470</string>
    <null/>
    <string>PER-013</string>
    <string>ServiceRequest</string>
    <string>CID-009</string>
    <string>SP-004</string>
    <string>SG-002</string>
</row>
<row>
    <string>SR-009626</string>
    <null/>
    <string>PER-017</string>
    <string>ServiceRequest</string>
    <string>CID-001</string>
    <string>SP-002</string>
    <string>SG-001</string>
</row>
<row>
    <string>HR-035112</string>
    <string>PER-029</string>
    <null/>
    <string>HelpRequest</string>
    <string>CID-015</string>
    <string>SP-002</string>
    <string>SG-001</string>
</row>
<row>
    <string>HR-028904</string>
    <string>PER-024</string>
    <null/>
    <string>HelpRequest</string>
    <string>CID-009</string>
    <string>SP-004</string>
    <string>SG-002</string>
</row>
</result>

这是我正在使用的 XSLT。
我通过使用键得到了其他唯一值。

<xsl:transform version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="xml" version="1.0" encoding="UTF-8" indent="yes"/>

    <xsl:key name="support_id" match="*" use="child::*[6]"/>
    <xsl:key name="support_grp_id" match="*" use="child::*[7]"/>
    <xsl:key name="company_id" match="*" use="child::*[5]"/>
    <!-- 
    <xsl:key name="customer_id" match="*" use="**???**"/>
    -->
    
    <xsl:template match="/">
        <data>
        <xsl:for-each select="result/row">
            <xsl:if test="child::*[4] = 'HelpRequest'">
                <work_order>
                    <work_order_id><xsl:value-of select = "child::*[1]"/></work_order_id>
                    <customer_id><xsl:value-of select = "child::*[2]"/></customer_id>
                    <work_type><xsl:value-of select = "child::*[4]"/></work_type>
                    <company_id><xsl:value-of select = "child::*[5]"/></company_id>
                    <support_id><xsl:value-of select = "child::*[6]"/></support_id>
                    <support_grp_id><xsl:value-of select = "child::*[7]"/></support_grp_id>
                </work_order>
            </xsl:if>
            <xsl:if test="child::*[4] = 'ServiceRequest'">
                <work_order>
                    <work_order_id><xsl:value-of select = "child::*[1]"/></work_order_id>
                    <customer_id><xsl:value-of select = "child::*[3]"/></customer_id>
                    <work_type><xsl:value-of select = "child::*[4]"/></work_type>
                    <company_id><xsl:value-of select = "child::*[5]"/></company_id>
                    <support_id><xsl:value-of select = "child::*[6]"/></support_id>
                    <support_grp_id><xsl:value-of select = "child::*[7]"/></support_grp_id>
                </work_order>
            </xsl:if>
        </xsl:for-each>
        <xsl:for-each select="//*[generate-id() = generate-id(key('support_id',child::*[6])[1])]">
            <support>
                <support_id><xsl:value-of select = "child::*[6]"/></support_id>
            </support>
        </xsl:for-each>
        <xsl:for-each select="//*[generate-id() = generate-id(key('support_grp_id',child::*[7])[1])]">
            <support_grp>
                <support_grp_id><xsl:value-of select = "child::*[7]"/></support_grp_id>
            </support_grp>
        </xsl:for-each>
        <xsl:for-each select="//*[generate-id() = generate-id(key('company_id',child::*[5])[1])]">
            <company>
                <company_id><xsl:value-of select = "child::*[5]"/></company_id>
            </company>
        </xsl:for-each>
        <!-- Problem...
        <xsl:for-each select="//*[generate-id() = generate-id(key('customer_id', **???**)[1])]">
            <customer>
                <customer_id><xsl:value-of select = "child::*[ **??? 2 OR 3 ???** ]"/></customer_id>
            </customer>
        </xsl:for-each>
        -->
        </data>
    </xsl:template>
    
</xsl:transform>

结果需要是:

<data>
    <work_order>
        <work_order_id>HR-039780</work_order_id>
        <customer_id>PER-013</customer_id>
        <work_type>HelpRequest</work_type>
        <company_id>CID-009</company_id>
        <support_id>SP-004</support_id>
        <support_grp_id>SG-002</support_grp_id>
    </work_order>
    <work_order>
        <work_order_id>SR-003470</work_order_id>
        <customer_id>PER-013</customer_id>
        <work_type>ServiceRequest</work_type>
        <company_id>CID-009</company_id>
        <support_id>SP-004</support_id>
        <support_grp_id>SG-002</support_grp_id>
    </work_order>
    <work_order>
        <work_order_id>SR-009626</work_order_id>
        <customer_id>PER-017</customer_id>
        <work_type>ServiceRequest</work_type>
        <company_id>CID-001</company_id>
        <support_id>SP-002</support_id>
        <support_grp_id>SG-001</support_grp_id>
    </work_order>
    <work_order>
        <work_order_id>HR-035112</work_order_id>
        <customer_id>PER-029</customer_id>
        <work_type>HelpRequest</work_type>
        <company_id>CID-015</company_id>
        <support_id>SP-002</support_id>
        <support_grp_id>SG-001</support_grp_id>
    </work_order>
    <work_order>
        <work_order_id>HR-028904</work_order_id>
        <customer_id>PER-024</customer_id>
        <work_type>HelpRequest</work_type>
        <company_id>CID-009</company_id>
        <support_id>SP-004</support_id>
        <support_grp_id>SG-002</support_grp_id>
    </work_order>
    <support>
        <support_id>SP-002</support_id>
    </support>
    <support>
        <support_id>SP-004</support_id>
    </support>
    <support_grp>
        <support_grp_id>SG-002</support_grp_id>
    </support_grp>
    <support_grp>
        <support_grp_id>SG-001</support_grp_id>
    </support_grp>
    <company>
        <company_id>CID-001</company_id>
    </company>
    <company>
        <company_id>CID-015</company_id>
    </company>
    <company>
        <company_id>CID-009</company_id>
    </company>
    <customer>
        <customer_id>PER-013</customer_id>
    </customer>
    <customer>
        <customer_id>PER-024</customer_id>
    </customer>
    <customer>
        <customer_id>PER-017</customer_id>
    </customer>
    <customer>
        <customer_id>PER-029</customer_id>
    </customer>
</data>

use="string[2]" 键和 <xsl:value-of select = "string[2]"/> 应该可以,如果我没有误解你的输入的话。对于所有的键,似乎使用 match="row" 而不是 match="*" 就足够了,而且效率更高。