0

I would like to transform some XML using XSLT that involves recursion. The source XML format is:

<?xml version="1.0" encoding="ISO-8859-1"?>
<Products>
  <Product Status="Updated" Type="Both">
    <GUID>cca0c671-7070-411d-91e8-895361b53e19</GUID>
    <ProductID>48936</ProductID>
    <Description>Main Product 1</Description>
    <Sequence>357</Sequence>
    <LastModifiedTimeStamp>2013-06-06</LastModifiedTimeStamp>
    <Parts>
      <ProductPart PartType="Individual">
        <Name>Individual Part 1-1</Name>
        <GUID>a06ac00e-96ed-4c70-8040-6a280bfc8cf2</GUID>
        <Quantity>3</Quantity>
      </ProductPart>
      <ProductPart PartType="Individual">
        <Name>Individual Part 1-2</Name>
        <GUID>a06ac00e-96ed-4c70-8040-6a280bfc8cf2</GUID>
        <Quantity>1</Quantity>
      </ProductPart>
      <ProductPart PartType="SubProduct">
        <Name>Sub Product 2</Name>
        <GUID>a06ac00e-96ed-4c70-8040-6a280bfc8cf2</GUID>
        <Quantity>1</Quantity>
        <SubParts>
          <ProductPart PartType="Individual">
            <Name>Individual Part 2-1</Name>
            <GUID>a06ac00e-96ed-4c70-8040-6a280bfc8cf2</GUID>
            <Quantity>5</Quantity>
          </ProductPart>
          <ProductPart PartType="Individual">
            <Name>Individual Part 2-2</Name>
            <GUID>a06ac00e-96ed-4c70-8040-6a280bfc8cf2</GUID>
            <Quantity>10</Quantity>
          </ProductPart>
          <ProductPart PartType="SubProduct">
            <Name>Sub Product 3</Name>
            <GUID>a06ac00e-96ed-4c70-8040-6a280bfc8cf2</GUID>
            <Quantity>2</Quantity>
            <SubParts>
              <ProductPart PartType="Individual">
                <Name>Individual Part 3-1</Name>
                <GUID>a06ac00e-96ed-4c70-8040-6a280bfc8cf2</GUID>
                <Quantity>6</Quantity>
              </ProductPart>
            </SubParts>
          </ProductPart>
        </SubParts>
      </ProductPart>
    </Parts>
  </Product>
</Products>

Target XML:

<Products>
  <Product>
    <GUID>cca0c671-7070-411d-91e8-895361b53e19</GUID>
    <ProductID>48936</ProductID>
    <Description>Main Product 1</Description>
    <Sequence>357</Sequence>
    <LastModifiedTimeStamp>2013-06-06</LastModifiedTimeStamp>
    <Subproducts>
      <ProductPart PartType="SubProduct">
        <Name>Sub Product 2</Name>
        <GUID>a06ac00e-96ed-4c70-8040-6a280bfc8cf2</GUID>
        <Quantity>1</Quantity>
        <Subproducts>
          <ProductPart PartType="SubProduct">
            <Name>Sub Product 3</Name>
            <GUID>a06ac00e-96ed-4c70-8040-6a280bfc8cf2</GUID>
            <Quantity>2</Quantity>
            <Subproducts />
            <Subparts>
              <ProductPart PartType="Individual">
                <Name>Individual Part 3-1</Name>
                <GUID>a06ac00e-96ed-4c70-8040-6a280bfc8cf2</GUID>
                <Quantity>6</Quantity>
              </ProductPart>
            </Subparts>
          </ProductPart>
        </Subproducts>
        <Subparts>
          <ProductPart PartType="Individual">
            <Name>Individual Part 2-1</Name>
            <GUID>a06ac00e-96ed-4c70-8040-6a280bfc8cf2</GUID>
            <Quantity>5</Quantity>
          </ProductPart>
          <ProductPart PartType="Individual">
            <Name>Individual Part 2-2</Name>
            <GUID>a06ac00e-96ed-4c70-8040-6a280bfc8cf2</GUID>
            <Quantity>10</Quantity>
          </ProductPart>
        </Subparts>
      </ProductPart>
    </Subproducts>
    <Subparts>
      <ProductPart PartType="Individual">
        <Name>Individual Part 1-1</Name>
        <GUID>a06ac00e-96ed-4c70-8040-6a280bfc8cf2</GUID>
        <Quantity>3</Quantity>
      </ProductPart>
      <ProductPart PartType="Individual">
        <Name>Individual Part 1-2</Name>
        <GUID>a06ac00e-96ed-4c70-8040-6a280bfc8cf2</GUID>
        <Quantity>1</Quantity>
      </ProductPart>
    </Subparts>
  </Product>
</Products>

Could someone please help me with the XSLT? I haven't done much work on XML transformation before and am in desperate need for help

EDIT: The XSLT I have written is as follows:

<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="1.0"
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:msxsl="urn:schemas-microsoft-com:xslt"
    exclude-result-prefixes="msxsl">

  <xsl:template match='/Products'>
    <Products>
      <xsl:apply-templates select='Product'/>
    </Products>
  </xsl:template>

  <xsl:template match='Product'>
    <Product>
      <GUID>
        <xsl:value-of select='GUID'/>
      </GUID>
      <ProductID>
        <xsl:value-of select='ProductID'/>
      </ProductID>
      <Description>
        <xsl:value-of select='Description'/>
      </Description>
      <Sequence>
        <xsl:value-of select='Sequence'/>
      </Sequence>
      <LastModifiedTimeStamp>
        <xsl:value-of select='LastModifiedTimeStamp'/>
      </LastModifiedTimeStamp>
      <Subproducts>
        <xsl:apply-templates select='Parts/ProductPart'>
          <xsl:with-param name="SubPartParam" select="''" />
        </xsl:apply-templates>
      </Subproducts>
      <Subparts>
        <xsl:apply-templates select='Parts/ProductPart'>
          <xsl:with-param name="SubPartParam" select="'Yes'" />
        </xsl:apply-templates>
      </Subparts>
    </Product>
  </xsl:template>

  <xsl:template match='ProductPart'>
    <xsl:param name="SubPartParam"/>

    <xsl:choose>

      <xsl:when test="($SubPartParam='' and @IngredientType='SubProduct')">
        <ProductPart>
          <xsl:attribute name='PartType'>
            <xsl:value-of select='@PartType'/>
          </xsl:attribute>
          <xsl:apply-templates select='ProductPart' />
          <Name>
            <xsl:value-of select='Name'/>
          </Name>
          <GUID>
            <xsl:value-of select='GUID'/>
          </GUID>
          <Quantity>
            <xsl:value-of select='Quantity'/>
          </Quantity>
        </ProductPart>
      </xsl:when>

      <xsl:when test="($SubPartParam='Yes' and @IngredientType='Individual')">
        <ProductPart>
          <xsl:attribute name='PartType'>
            <xsl:value-of select='@PartType'/>
          </xsl:attribute>
          <xsl:apply-templates select='ProductPart' />
          <Name>
            <xsl:value-of select='Name'/>
          </Name>
          <GUID>
            <xsl:value-of select='GUID'/>
          </GUID>
          <Quantity>
            <xsl:value-of select='Quantity'/>
          </Quantity>
        </ProductPart>
      </xsl:when>

    </xsl:choose>

  </xsl:template>

</xsl:stylesheet>
4

1 回答 1

0

该样式表按照您的要求执行。它非常简单,只涉及以不同的顺序复制每个下方的ProductPart元素。ProductProductPart

困难的部分是从输入输出XML 数据集推导出规则。如果你用英语描述了你想要的东西,那会很有帮助。

我希望这有帮助。输出与您的"Target XML"相同。

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

  <xsl:strip-space elements="*"/>
  <xsl:output method="xml" indent="yes" omit-xml-declaration="yes"/>

  <xsl:template match="/Products">
    <xsl:copy>
      <xsl:apply-templates select="Product"/>
    </xsl:copy>
  </xsl:template>

  <xsl:template match="Product">
    <xsl:copy>
      <xsl:copy-of select="GUID"/>
      <xsl:copy-of select="ProductID"/>
      <xsl:copy-of select="Description"/>
      <xsl:copy-of select="Sequence"/>
      <xsl:copy-of select="LastModifiedTimeStamp"/>
      <Subproducts>
        <xsl:apply-templates select="Parts/ProductPart[@PartType='SubProduct']"/>
      </Subproducts>
      <Subparts>
        <xsl:apply-templates select="Parts/ProductPart[@PartType='Individual']"/>
      </Subparts>
    </xsl:copy>
  </xsl:template>

  <xsl:template match="ProductPart">
    <xsl:copy>
      <xsl:copy-of select="@*"/>
      <xsl:copy-of select="Name"/>
      <xsl:copy-of select="GUID"/>
      <xsl:copy-of select="Quantity"/>
      <xsl:if test="@PartType = 'SubProduct'">
        <Subproducts>
          <xsl:apply-templates select="SubParts/ProductPart[@PartType='SubProduct']"/>
        </Subproducts>
        <Subparts>
          <xsl:apply-templates select="SubParts/ProductPart[@PartType='Individual']"/>
        </Subparts>
      </xsl:if>
    </xsl:copy>
  </xsl:template>

</xsl:stylesheet>
于 2013-06-07T13:28:38.753 回答