Damian Szarik Paul
Damian Szarik Paul

Reputation: 99

One xslt transform for many similar obiects/tags

I have two xml`s with almost the same content (difference depends on Java object generating that xml).

xml X:

    <responseXXXXcontent> 
      <contentonedeep>
        <contenttwodeep>
          <finalcontentXXXX>
            <name>zzz</name>
          </finalcontentXXXX>
        </ontenttwodeep>
      </contentonedeep>
    </responseXXXXcontent>

xml Y:

    <responseYYYYcontent> 
      <contentonedeep>
        <contenttwodeep>
          <finalcontentYYYY>
            <name>zzz</name>
          </finalcontentYYYY>
        </ontenttwodeep>
      </contentonedeep>
    </responseYYYYcontent>

As you see, only differences in tree tag (tag names) is that, in xml X we have 'XXXX' substring and in xml Y we have 'YYYY' substring.

What i need, is to make sentence, where i can read all content from that 2 different xml's without worrying if it reveices xml X or xml Y and use for it onle one xslt. I was thinking about something with ixsl:if statement and xsl:choose, but my ideas didn't work. I bet there is some fancy syntax which will allow me do that, something like:

<xsl:if test=node[@substring].equals("X/Y")>
  <xsl:apply-templates select=CHILD_OF_CURRENT_NODE>
  </xsl:apply-templates>
</xsl:if>

I am newbie if it goes to xslt so I will appreciate any help, thx!

Edit: My required output in that case is:

zzz

as a "name" content, independently from input.

I am using XSLT version 1.0 ;)

Upvotes: 0

Views: 81

Answers (2)

Michael Kay
Michael Kay

Reputation: 163587

Using union expressions and patterns as suggested by @michael.hor257k is certainly one approach.

However, I find it's often cleaner if you have multiple variants of an XML vocabulary, to preprocess each document into a standard form before applying your main transformation. This avoids complicating the logic of your main transformation (which can grow like topsy as more variants come along), and the preprocessing code is re-usable - it can be applied to any processing pipeline.

For the specific case you mention, there's another approach that might not be immediately obvious. You could define a schema that accommodates both structures by using substitution groups, and then in a schema-aware transformation you can select any element in the substitution group using the syntax element(subst-group-name).

Upvotes: 1

michael.hor257k
michael.hor257k

Reputation: 117102

The simplest solution, IMHO, is to refer to the elements whose name can change as the union of both variants - for example:

<xsl:template match="responseXXXXcontent|responseYYYYcontent">
    <!-- ... -->
</xsl:template>

or:

<xsl:apply-templates select="finalcontentXXXX|finalcontentYYYY"/>

Upvotes: 1

Related Questions