XSLT объединяет несколько узлов под одним родителем - PullRequest
0 голосов
/ 14 февраля 2019

Входной XML -

<Operations>
     <ID>10</ID>
     <UserArea>
        <AdditionalPhantomInformation>
            <PhantomItem>
                <ItemCode>41341288</ItemCode>
                <SubComponent>40241289</SubComponent>
                <Position>1</Position>
            </PhantomItem>
        </AdditionalPhantomInformation>
    </UserArea>
    <ConsumedItem>          
        <LineNumber>3</LineNumber>
        <ParentItem>40241288</ParentItem>
    </ConsumedItem>
    <UserArea>
        <AdditionalPhantomInformation>
            <PhantomItem>
                <ItemCode>41341288</ItemCode>
                <SubComponent>40241302</SubComponent>
                <Position>5</Position>
            </PhantomItem>
        </AdditionalPhantomInformation>
    </UserArea>
</Operations>

И мой ожидаемый вывод -

    <Operations>
        <ID>10</ID>
        <UserArea>
            <AdditionalPhantomInformation>
                <PhantomItem>
                    <ItemCode>41341288</ItemCode>
                    <SubComponent>40241289</SubComponent>
                   <Position>1</Position>
                </PhantomItem>
                <PhantomItem>
                    <ItemCode>41341288</ItemCode>
                    <SubComponent>40241302</SubComponent>
                    <Position>5</Position>
                </PhantomItem>  
            </AdditionalPhantomInformation>
        </UserArea>
        <ConsumedItem>            
          <LineNumber>3</LineNumber>
          <ParentItem>40241288</ParentItem>
        </ConsumedItem>
    </Operations>  

Я искал различные источники и пытался, но я не могу правильно получить xslt.Я не знаю, как использовать xsl: для каждой группы.Пожалуйста помоги.Я использую XSLT 2.0.

1 Ответ

0 голосов
/ 14 февраля 2019

Вам не обязательно нужен xsl:for-each-group здесь, так как все, что вы делаете, это объединение определенных узлов в один.

Начните с шаблона идентификации ...

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

Или, если бы вы могли использовать XSLT 3.0 ....

<xsl:mode on-no-match="shallow-copy"/>

, тогда иметь шаблон, соответствующий первому UserArea, который выполняет объединение ...

  <xsl:template match="UserArea[1]">
    <xsl:copy>
      <xsl:apply-templates select="node()|following-sibling::UserArea/node()" />
    </xsl:copy>
  </xsl:template>

Вы бы тогдапросто нужен другой шаблон, чтобы другие UserArea элементы не выводились в исходное положение.

<xsl:template match="UserArea" />

Попробуйте это XSLT

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

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

  <xsl:template match="UserArea[1]">
    <xsl:copy>
      <xsl:apply-templates select="node()|following-sibling::UserArea/node()" />
    </xsl:copy>
  </xsl:template>

  <xsl:template match="UserArea" />
</xsl:stylesheet>

Обратите внимание, если вы действительно хотите использовать xsl:for-each-group вы бы сделали это следующим образом

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

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

  <xsl:template match="Operations">
    <xsl:copy>
      <xsl:for-each-group select="*" group-by="name()">
        <xsl:choose>
          <xsl:when test="current-grouping-key() = 'UserArea'">
            <xsl:copy>
              <xsl:apply-templates select="current-group()/node()" />
            </xsl:copy>
          </xsl:when>
          <xsl:otherwise>
            <xsl:apply-templates select="current-group()" />
          </xsl:otherwise>
        </xsl:choose>
      </xsl:for-each-group>
    </xsl:copy>
  </xsl:template>
</xsl:stylesheet>

Преимущество в том, что вы легко расширяетесь, если у вас есть узлы, отличные от UserArea, которые вы хотите объединить.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...