Link to home
Start Free TrialLog in
Avatar of tesmc
tesmcFlag for United States of America

asked on

XSL: find matching Traveler by position in XML (since no unique identifier is found)

I have the following xsl and input file.
I want to populate Loyal/@givenName & Loyal/@surname by matching the TravelerID with the POSITION of where TravelerName exists.

Example:

TravelerIDs[@ID=T1]/Info/FFNumber  is linked to the 2nd Traveler in Request/TravelerName (i.e - JOHN DOE )
The way the TravelerName's are ordered is the same as the way the TravelerIds are odered



input file
<root>
	<Request>
		<TravelerName>
			<Surname>DOE</Surname>
			<GivenName>JANE</GivenName>
		</TravelerName>
		<TravelerName>
			<Surname>DOE</Surname>
			<GivenName>JOHN</GivenName>
		</TravelerName>
		<TravelerIDs ID="T2" Type="ADT"/>
		<TravelerIDs ID="T1" Type="ADT">
			<Info>
				<FFNumber>1234</FFNumber>
				<FFCompanyCode>RT</FFCompanyCode>
			</Info>
		</TravelerIDs>
	</Request>
</root>

Open in new window




xsl code:
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0">
  <xsl:output method="xml" indent="yes" omit-xml-declaration="yes" encoding="UTF-8"/>

  <xsl:template match="/root">
    <Request>
      <xsl:for-each select="Request/TravelerIDs">
        <Qualifiers>
          <xsl:attribute name="Type">
            <xsl:value-of select="@Type"/>
          </xsl:attribute>
          <Traveler>
            <xsl:value-of select="translate ( @ID, 'T', '')"/>
          </Traveler>
          <xsl:if test="Info">
            <Loyal>
              <xsl:attribute name="code">
                <xsl:value-of select="Info/FFCompanyCode"/>
              </xsl:attribute>
              <xsl:attribute name="givenName">
                <xsl:value-of select="../Traveler/TravelerName/GivenName"/>
              </xsl:attribute>
              <xsl:attribute name="surname">
                <xsl:value-of select="../Traveler/TravelerName/Surname"/>
              </xsl:attribute>
              <xsl:value-of select="FQTVInfo/FFNumber"/>
            </Loyal>
          </xsl:if>
        </Qualifiers>
      </xsl:for-each>
    </Request>
  </xsl:template>
</xsl:stylesheet>

Open in new window

ASKER CERTIFIED SOLUTION
Avatar of Gertone (Geert Bormans)
Gertone (Geert Bormans)
Flag of Belgium image

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
Avatar of tesmc

ASKER

that worked

can you please explain how you are doing this?
this variable
                <xsl:variable name="position" select="position() - 1"></xsl:variable>
counts the number of TravelerIDs before the current TravelerIDs

I then use that variable in this expression
../TravelerName[count(preceding-sibling::TravelerName) = $position]
is the TravelerName that has a number of preceding sibling TravelerName elements equal to $position
in other words: it returns the TravelerName at the exact relative position as the TravelerIds we are currently processing
Avatar of tesmc

ASKER

Thank u