otesanek
otesanek

Reputation: 57

xslt - format new xml structure

Given XML:

<?xml version="1.0" encoding="utf-8"?>
<RUNRESULT STATE="SUCCESS" START="2020-09-07 08:48:11" STOP="2020-09-07 08:48:13" DATABASENUMBER="10" TRANSFORMATION="0000036">
  <DETAIL>
    <RECORD SUBJECTID="70521192" CLASSID="343" GUNID="00000A00009J15ZII0" FOLDERID="14858" REFERENCE="pro repliku" NAME="PRO VYVOLÁNÍ REPLIKACE DO MODULY" CLASSNAME="Kmenová karta zboží / materiálu" FOLDERNAME="Modula - pomocný" TIMESTAMP="0000000061FBCCDF" datum_vzniku="2020-08-17 10:55:25" last_update="2020-09-07 08:47:29" />
  </DETAIL>
  <storedProcedureResult>
    <items>
      <item>
        <RECORD SUBJECTID="70521192" CLASSID="343" GUNID="00000A00009J15ZII0" FOLDERID="14858" REFERENCE="pro repliku" NAME="PRO VYVOLÁNÍ REPLIKACE DO MODULY" CLASSNAME="Kmenová karta zboží / materiálu" FOLDERNAME="Modula - pomocný" TIMESTAMP="0000000061FBCCDF" datum_vzniku="2020-08-17 10:55:25" last_update="2020-09-07 08:47:29" />
        <Datastores>
          <Datastore TableName="invoiceHeader">
            <Definition>
              <Columns>
                <Column Name="c_cs" DataType="int" />
                <Column Name="c_objed" DataType="string" />
              </Columns>
            </Definition>
            <DataRows>
              <DataRow c_cs="68306186" c_objed="ODH2001295" />
              <DataRow c_cs="68402059" c_objed="ODH2001296" />
</DataRows>
      </Datastore>

<Datastore TableName="invoiceItems">
        <Definition>
          <Columns>
            <Column Name="c_cs" DataType="int" />
            <Column Name="c_objed" DataType="string" />
            <Column Name="odber_dodav" DataType="string" />
            <Column Name="ORD_TIPOOP" DataType="string" />
            <Column Name="zdroj_ref" DataType="string" />
            <Column Name="poc" DataType="decimal" />
            <Column Name="c_r" DataType="int" />
          </Columns>
        </Definition>
        <DataRows>
          <DataRow c_cs="68306186" c_objed="ODH2001295" odber_dodav="Divize ND + SERVIS" ORD_TIPOOP="P" zdroj_ref="XXX1" poc="1.000000" c_r="13" />
          <DataRow c_cs="68306186" c_objed="ODH2001295" odber_dodav="Divize ND + SERVIS" ORD_TIPOOP="P" zdroj_ref="XXX2" poc="1.000000" c_r="15" />
          <DataRow c_cs="68306186" c_objed="ODH2001295" odber_dodav="Divize ND + SERVIS" ORD_TIPOOP="P" zdroj_ref="XXX3" poc="4.000000" c_r="17" />
          <DataRow c_cs="68306186" c_objed="ODH2001295" odber_dodav="Divize ND + SERVIS" ORD_TIPOOP="P" zdroj_ref="XXX4" poc="2.000000" c_r="18" />
          <DataRow c_cs="68306186" c_objed="ODH2001295" odber_dodav="Divize ND + SERVIS" ORD_TIPOOP="P" zdroj_ref="XXX5" poc="1.000000" c_r="19" />
          <DataRow c_cs="68306186" c_objed="ODH2001296" odber_dodav="Divize ND + SERVIS" ORD_TIPOOP="P" zdroj_ref="YYY1" poc="2.000000" c_r="21" />
          <DataRow c_cs="68306186" c_objed="ODH2001296" odber_dodav="Divize ND + SERVIS" ORD_TIPOOP="P" zdroj_ref="YYY2" poc="30.000000" c_r="22" />
          <DataRow c_cs="68306186" c_objed="ODH2001296" odber_dodav="Divize ND + SERVIS" ORD_TIPOOP="P" zdroj_ref="YYY3" poc="1.000000" c_r="23" />
          <DataRow c_cs="68306186" c_objed="ODH2001296" odber_dodav="Divize ND + SERVIS" ORD_TIPOOP="P" zdroj_ref="YYY4" poc="1.000000" c_r="24" />
          <DataRow c_cs="68306186" c_objed="ODH2001296" odber_dodav="Divize ND + SERVIS" ORD_TIPOOP="P" zdroj_ref="YYY5" poc="1.000000" c_r="25" />
</DataRows>
          </Datastore>
        </Datastores>
      </item>
    </items>
  </storedProcedureResult>
</RUNRESULT>

Given XSLT:

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

    <xxx>
        <objednavka>
            <hlavicka>
            <xsl:for-each select="/RUNRESULT/storedProcedureResult/items/item/Datastores/Datastore[1]/DataRows/DataRow">
                <c_objed>
                    <xsl:value-of select="@c_objed"/>
                </c_objed>
                <polozka>
                <xsl:for-each select="/RUNRESULT/storedProcedureResult/items/item/Datastores/Datastore[2]/DataRows/DataRow">
                    <zdroj_ref>
                        <xsl:value-of select="@zdroj_ref"/>
                    </zdroj_ref>
                </xsl:for-each>
            </polozka>
                </xsl:for-each>
            </hlavicka>
        </objednavka>
    </xxx>
</xsl:template>
</xsl:stylesheet>

Output looks like this:

<xxx>
   <objednavka>
      <hlavicka>
         <c_objed>ODH2001295</c_objed>
         <polozka>
            <zdroj_ref>XXX1</zdroj_ref>
            <zdroj_ref>XXX2</zdroj_ref>
            <zdroj_ref>XXX3</zdroj_ref>
            <zdroj_ref>XXX4</zdroj_ref>
            <zdroj_ref>XXX5</zdroj_ref>
            <zdroj_ref>YYY1</zdroj_ref>
            <zdroj_ref>YYY2</zdroj_ref>
            <zdroj_ref>YYY3</zdroj_ref>
            <zdroj_ref>YYY4</zdroj_ref>
            <zdroj_ref>YYY5</zdroj_ref>
         </polozka>
       </hlavicka>

       <hlavicka>
            <c_objed>ODH2001296</c_objed>
         <polozka>
            <zdroj_ref>XXX1</zdroj_ref>
            <zdroj_ref>XXX2</zdroj_ref>
            <zdroj_ref>XXX3</zdroj_ref>
            <zdroj_ref>XXX4</zdroj_ref>
            <zdroj_ref>XXX5</zdroj_ref>
            <zdroj_ref>YYY1</zdroj_ref>
            <zdroj_ref>YYY2</zdroj_ref>
            <zdroj_ref>YYY3</zdroj_ref>
            <zdroj_ref>YYY4</zdroj_ref>
            <zdroj_ref>YYY5</zdroj_ref>
         </polozka>
        </hlavicka>

Desired output:

<xxx>
    <objednavka>
        <hlavicka>
            <c_objed>ODH2001295</c_objed>
                <polozka>
                    <zdroj_ref>XXX1</zdroj_ref>
                    <zdroj_ref>XXX2</zdroj_ref>
                    <zdroj_ref>XXX3</zdroj_ref>
                    <zdroj_ref>XXX4</zdroj_ref>
                    <zdroj_ref>XXX5</zdroj_ref>
                </polozka>
        </hlavicka>
        <hlavicka>
            <c_objed>ODH2001296</c_objed>
                <polozka>
                    <zdroj_ref>YYY1</zdroj_ref>
                    <zdroj_ref>YYY2</zdroj_ref>
                    <zdroj_ref>YYY3</zdroj_ref>
                    <zdroj_ref>YYY4</zdroj_ref>
                    <zdroj_ref>YYY5</zdroj_ref>
                </polozka>
        </hlavicka>
    </objednavka>
</xxx>

I think I need to write some criteria in <xsl:value-of select="@zdroj_ref"/> and it should be something like this

<xsl:value-of select="@zdroj_ref if @c_objed(header) == @c_objed(items) "/>

Right now I'm getting always every items data for each header.

Basically I want to display only a data that corresponds with header and items values.

Upvotes: 0

Views: 39

Answers (1)

michael.hor257k
michael.hor257k

Reputation: 117102

If I understand this correctly (which is not at all certain), your XML contains a list of invoice headers and a list of invoice items, cross-referenced by a common c_objed value.

If this is true, I would suggest you use a key to resolve the cross-references. Something like:

XSLT 1.0

<xsl:stylesheet 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:strip-space elements="*"/>

<xsl:key name="items" match="Datastore[@TableName='invoiceItems']/DataRows/DataRow" use="@c_objed" />

<xsl:template match="/RUNRESULT">
    <xxx>
        <!-- for each invoice header -->
        <xsl:for-each select="storedProcedureResult/items/item/Datastores/Datastore[@TableName='invoiceHeader']/DataRows/DataRow">
            <objednavka>
                <hlavicka>
                    <c_objed>
                        <xsl:value-of select="@c_objed"/>
                    </c_objed>
                </hlavicka>
                <polozka>
                    <!-- get matching items -->
                    <xsl:for-each select="key('items', @c_objed)">
                        <zdroj_ref>
                            <xsl:value-of select="@zdroj_ref"/>
                        </zdroj_ref>
                    </xsl:for-each>
                </polozka>
            </objednavka>
        </xsl:for-each>
    </xxx>
</xsl:template>
    
</xsl:stylesheet>

Upvotes: 1

Related Questions