基于2个XMLs创建XML,并使用XSLT2.0在两个文件中查找值。

问题描述 投票:0回答:1

我试图基于另外2个XML生成一个XML。我正在对一个DB进行轮询,该DB返回了人们的详细信息(在查询中可以有n个数量的人返回)。最终的XML应该有准确的数量 数据标签 作为 不同名称标签 在来自DB的XML中. 例如

第1个XML--从DB中获取这个

<parent>
    <child>
        <name>John</name>
        <city>Boston</city>
    </child>
    <child>
        <name>John</name>
        <city>Seattle</city>
    </child>
    <child>
        <name>Allison</name>
        <city>Houston</city>
    </child>
</parent>

第2个XML--从另一个源头获得

<details>
    <parent>
        <detail>
            <city>Boston</city>
            <code>abc</code>
        </detail>
        <detail>
            <city>Houston</city>
            <code>xyz</code>
        </detail>
    </parent>
    <parent>
        <detail>
            <city>Boston</city>
            <code>abc</code>
        </detail>
        <detail>
            <city>Seattle</city>
            <code>mno</code>
        </detail>
    </parent>
    <parent>
        <detail>
            <city>Houston</city>
            <code>xyz</code>
        </detail>
        <detail>
            <city>Seattle</city>
            <code>mno</code>
        </detail>
    </parent>
</details>

首先,我需要创建2个数据标签,因为有2个不同的名字--John和Allison(这部分已经完成并运行良好).然后,我需要检查John,无论在DB行中是否存在独特的城市标签。让我们考虑一下第1个XML,我们有John与波士顿和西雅图有关。所以,我将逐一检查这些城市在第2个XML中的情况,并为每一个 父母 标签,我匹配的东西,我会创建一个新的标签。细节 并粘贴所有相关内容。

1)如果没有匹配的条目,就不要创建详情标签,因为没有匹配的条目。

2)如果没有匹配的条目,则不要创建详情标签,因为没有匹配的条目。城市 标签下会出现一个 父母 标签。的值。城市 标签将是UNIQUE,在 父母 标签。我必须配合 城市 并从所有匹配的XML中取值。城市 标签,跨越所有来自第2个XML的父标签,并以一种方式填充,即在 父母 标签进入各自的 详细 标签的输出XML。PFB的XML示例,这将是一个更好的解释方式 - 。

最终预期的XML-

<FinalData>
    <Data>
        <name>John</name>
        <details>
            <detail>
                <city value="Boston">abc</city>
            </detail>
            <detail>
                <city value="Boston">abc</city>
                <city value="Seattle">mno</city>
            </detail>
            <detail>
                <city value="Seattle">mno</city>
            </detail>
        </details>
    </Data>
    <Data>
        <name>Allison</name>
        <details>
            <detail>
                <city value="Houston">xyz</city>
            </detail>
            <detail>
                <city value="Houston">xyz</city>
            </detail>
        </details>
    </Data>
</FinalData>

目前我的XSLT的结果是这样的------。

<FinalData>
    <Data>
        <name>John</name>
        <details>
            <detail>
                <city value="Boston">abc</city>
                <city value="Boston">abc</city>
                <city value="Seattle">mno</city>
                <city value="Seattle">mno</city>
            </detail>
        </details>
    </Data>
    <Data>
        <name>Allison</name>
        <details>
            <detail>
                <city value="Houston">xyz</city>
                <city value="Houston">xyz</city>
            </detail>
        </details>
    </Data>
</FinalData>

希望这很清楚,因为我不是一个善于解释的人。

xml xslt xslt-2.0 xslt-grouping xslkey
1个回答
0
投票

使用键来解决交叉引用。

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:xs="http://www.w3.org/2001/XMLSchema"
    exclude-result-prefixes="#all"
    version="3.0">

  <xsl:param name="details">
<details>
    <parent>
        <detail>
            <city>Boston</city>
            <code>abc</code>
        </detail>
        <detail>
            <city>Houston</city>
            <code>xyz</code>
        </detail>
    </parent>
    <parent>
        <detail>
            <city>Boston</city>
            <code>abc</code>
        </detail>
        <detail>
            <city>Seattle</city>
            <code>mno</code>
        </detail>
    </parent>
    <parent>
        <detail>
            <city>Houston</city>
            <code>xyz</code>
        </detail>
        <detail>
            <city>Seattle</city>
            <code>mno</code>
        </detail>
    </parent>
</details>      
  </xsl:param>

  <xsl:key name="parent-ref" match="parent" use="detail/city"/>
  <xsl:key name="detail-ref" match="parent/detail" use="city"/>

  <xsl:output method="xml" indent="yes" />

  <xsl:template match="parent">
    <FinalData>
        <xsl:for-each-group select="child" group-by="name">
            <Data>
                <xsl:copy-of select="name"/>
            </Data>
            <Details>
                <xsl:apply-templates select="key('parent-ref', current-group()/city, $details)"/>
            </Details>
        </xsl:for-each-group>
    </FinalData>
  </xsl:template>

  <xsl:template match="details/parent">
      <detail>
          <xsl:apply-templates select="key('detail-ref', current-group()/city, .)"/>
      </detail>
  </xsl:template>

  <xsl:template match="detail">
      <city value="{city}">
          <xsl:value-of select="code"/>
      </city>
  </xsl:template>

</xsl:stylesheet>

https:/xsltfiddle.liberty-development.netgVhDDyY

为了完整起见,第二个文档是内联的,但你当然可以使用 <xsl:param name="details" select="doc('details.xml')"/> 而不是。

© www.soinside.com 2019 - 2024. All rights reserved.