tags:

views:

39

answers:

1

I have a specific problem getting values for width and height out of some XML that has namespace prefixes defined. I can get other values such as SomeText from RelatedMaterial quite easily using normal xpath with namespace "n:" but unable to get values for width and height.

Sample XML:

<Description>
<Information>
<GroupInformation xml:lang="en">
 <BasicDescription>
  <RelatedMaterial>
   <SomeText>Hello</SomeText>
   <t:ContentProperties>
    <t:ContentAttributes>
     <t:Width>555</t:Width>
     <t:Height>444</t:Height>
    </t:ContentAttributes>
   </t:ContentProperties>
  </RelatedMaterial>
 </BasicDescription>
</GroupInformation>
</Information>
</Description>

Here is an extract from the XSLT:

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:n="urn:t:myfoo:2010" xmlns:tva2="urn:t:myfoo:extended:2008"

<xsl:apply-templates select="n:Description/n:Information/n:GroupInformation"/>

<xsl:template match="n:GroupInformation">
  <width>
    <xsl:value-of select="n:BasicDescription/n:RelatedMaterial/t:ContentProperties/t:ContentAttributes/t:Width"/>
  </width>
</xsl:template>

The above XSLT does not work for getting the width. Any ideas?

+1  A: 

I'm not sure you have realised that both your input and XSLT is invalid, it's always better to provide working examples.

Anyway, if we look at the XPath expression n:BasicDescription/n:RelatedMaterial/t:ContentProperties/t:ContentAttributes/t:Width you're using a prefix n which is mapped to urn:t:myfoo:2010 but when the data infact is in the default namespace. The same goes for the t prefix which isn't defined at all in neither the input data nor XSLT.

You need to define the namespaces on "both sides", in the XML data and the XSLT transformation and they need to be the same, not the prefixes, but the URI.

Somebody else could probably explain this better than me.

I've corrected your example and added a few things to make this work.

Input:

<?xml version="1.0" encoding="UTF-8"?>
<Description 
  xmlns="urn:t:myfoo:2010" 
  xmlns:t="something...">
  <Information>
    <GroupInformation xml:lang="en">
      <BasicDescription>
        <RelatedMaterial>
          <SomeText>Hello</SomeText>
          <t:ContentProperties>
            <t:ContentAttributes>
              <t:Width>555</t:Width>
              <t:Height>444</t:Height>
            </t:ContentAttributes>
          </t:ContentProperties>
        </RelatedMaterial>
      </BasicDescription>
    </GroupInformation>
  </Information>
</Description>

XSLT:

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet 
  xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="2.0" 
  xmlns:n="urn:t:myfoo:2010" 
  xmlns:t="something...">

  <xsl:template match="/">
    <xsl:apply-templates select="n:Description/n:Information/n:GroupInformation"/>
  </xsl:template>

  <xsl:template match="n:GroupInformation">
    <xsl:element name="width">
      <xsl:value-of select="n:BasicDescription/n:RelatedMaterial/t:ContentProperties/t:ContentAttributes/t:Width"/>
    </xsl:element>
  </xsl:template>

</xsl:stylesheet>

Output:

<?xml version="1.0" encoding="UTF-8"?>
<width>555</width>
Per T