简体   繁体   English

在XSLT 1.0中进行匹配和合并

[英]Match and Merge in XSLT 1.0

I have a sample XML message which contains multiple parent node. 我有一个示例XML消息,其中包含多个父节点。 The requirement is something like if the two parent node are same, merge the child node. 要求就像两个父节点相同时,合并子节点。

Sample Input Message is 样本输入消息为

<document>
<party>
    <gtin>1000909090</gtin>
    <pos>
        <attrGroupMany name="temperatureInformation">
            <row>
                <attr name="temperatureCode">STORAGE</attr>
                <attrQualMany name="temperature">
                    <value qual="FAH">10</value>
                    <value qual="CC">20</value>
                </attrQualMany>
                <attrGroupMany name="temperatureStats">
                    <row>
                        <attr name="StatsCode">CODE1</attr>
                    </row>
                    <row>
                        <attr name="StatsCode">CODE2</attr>
                    </row>
                </attrGroupMany>
            </row>
            <row>
                <attr name="temperatureCode">STORAGE</attr>
                <attrQualMany name="temperature">
                    <value qual="FAH">10</value>
                    <value qual="CC">20</value>
                </attrQualMany>
                <attrGroupMany name="temperatureStats">
                    <row>
                        <attr name="StatsCode">CODE3</attr>
                    </row>
                    <row>
                        <attr name="StatsCode">CODE4</attr>
                    </row>
                </attrGroupMany>
            </row>
            <row>
                <attr name="temperatureCode">HANDLING</attr>
                <attrQualMany name="temperature">
                    <value qual="FAH">10</value>                    
                </attrQualMany>
                <attrGroupMany name="temperatureStats">
                    <row>
                        <attr name="StatsCode">CODE5</attr>
                    </row>
                    <row>
                        <attr name="StatsCode">CODE6</attr>
                    </row>
                </attrGroupMany>
            </row>
            <row>
                <attr name="temperatureCode">HANDLING</attr>
                <attrGroupMany name="temperatureStats">
                    <row>
                        <attr name="StatsCode">CODE7</attr>
                    </row>
                    <row>
                        <attr name="StatsCode">CODE8</attr>
                    </row>
                </attrGroupMany>
            </row>
        </attrGroupMany>
    </pos>
</party>
</document>

we need to concat the value of temperatureCode, All value of temperature (if present) for all row and if they are duplicate, then merge the row inside temperatureStats of the child in the parent. 我们需要合并温度代码的值,所有行的所有温度值(如果存在),如果它们是重复的,则将行合并到父级中子级的temperatureStats中。

Expected output is in the same structure. 预期输出的结构相同。 You can see the second node is merged with first 您可以看到第二个节点与第一个节点合并

<document>
<party>
    <gtin>1000909090</gtin>
    <pos>
        <attrGroupMany name="temperatureInformation">
            <row>
                <attr name="temperatureCode">STORAGE</attr>
                <attrQualMany name="temperature">
                    <value qual="FAH">10</value>
                    <value qual="CC">20</value>
                </attrQualMany>
                <attrGroupMany name="temperatureStats">
                    <row>
                        <attr name="StatsCode">CODE1</attr>
                    </row>
                    <row>
                        <attr name="StatsCode">CODE2</attr>
                    </row>
                    <row>
                        <attr name="StatsCode">CODE3</attr>
                    </row>
                    <row>
                        <attr name="StatsCode">CODE4</attr>
                    </row>
                </attrGroupMany>
            </row>
            <row>
                <attr name="temperatureCode">HANDLING</attr>
                <attrQualMany name="temperature">
                    <value qual="FAH">10</value>                    
                </attrQualMany>
                <attrGroupMany name="temperatureStats">
                    <row>
                        <attr name="StatsCode">CODE5</attr>
                    </row>
                    <row>
                        <attr name="StatsCode">CODE6</attr>
                    </row>
                </attrGroupMany>
            </row>
            <row>
                <attr name="temperatureCode">HANDLING</attr>
                <attrGroupMany name="temperatureStats">
                    <row>
                        <attr name="StatsCode">CODE7</attr>
                    </row>
                    <row>
                        <attr name="StatsCode">CODE8</attr>
                    </row>
                </attrGroupMany>
            </row>
        </attrGroupMany>
    </pos>
</party>
</document>

Any input will be very valuable. 任何投入都是非常有价值的。

I think you got a solution to group in a previous answer https://stackoverflow.com/a/38240246/252228 , you can then process the items in a group calling the key function: 我认为您可以在先前的答案https://stackoverflow.com/a/38240246/252228中对分组进行解决,然后可以在调用key函数的分组中处理项目:

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    version="1.0">

    <xsl:output indent="yes"/>


    <xsl:key name="group" match="attrGroupMany[@name = 'temperatureInformation']/row"
        use="concat(attr[@name = 'temperatureCode'], '|', attrQualMany[@name = 'temperature'])"/>

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

    <xsl:template match="attrGroupMany[@name = 'temperatureInformation']">
        <xsl:copy>
            <xsl:apply-templates select="@*"/>
            <xsl:apply-templates select="row[generate-id() = generate-id(key('group', concat(attr[@name = 'temperatureCode'], '|', attrQualMany[@name = 'temperature']))[1])]"/>
        </xsl:copy>
    </xsl:template>

    <xsl:template match="attrGroupMany[@name = 'temperatureStats']">
        <xsl:copy>
            <xsl:apply-templates select="@* | key('group', concat(../attr[@name = 'temperatureCode'], '|', ../attrQualMany[@name = 'temperature']))/attrGroupMany[@name = 'temperatureStats']/row"/>
        </xsl:copy>
    </xsl:template>

</xsl:stylesheet>

Note however that the whole approach of taking the string value of an element with varying child elements is brittle, if there is a difference in white space the value might be considered different. 但是请注意,获取具有变化的子元素的元素的字符串值的整个方法都很脆弱,如果空白存在差异,则可以认为该值是不同的。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM