Rate this page

Prevent unwanted namespace prefix declarations from being added by an XSLT stylesheet

Tested with xsltproc on

Debian (Etch, Lenny, Squeeze)
Ubuntu (Lucid, Maverick, Natty, Trusty)

Tested with Xalan on

Debian (Etch, Lenny, Squeeze)
Ubuntu (Lucid, Maverick, Natty, Trusty)

Tested with Saxon-B on

Debian (Lenny, Squeeze)
Ubuntu (Lucid, Maverick, Natty, Trusty)

Tested with Saxon-6 on

Debian (Etch, Lenny, Squeeze)
Ubuntu (Lucid, Maverick, Natty, Trusty)

Objective

To prevent a namespace prefix declaration in an XSLT stylesheet element from appearing in the output document

Background

An XML namespace prefix declaration is an attribute with the prefix xmlns which binds a namespace prefix to a URI, for example:

xmlns:xhtml="http://www.w3.org/1999/xhtml"

When a namespace prefix is declared in an XSLT stylesheet the declaration is normally copied into the output document. The reason for doing this is to ensure that any elements with that prefix can have their namespace correctly resolved if they appear in the output. However it may be that the prefix is only used during processing (for example, to recognise elements in the input document). In that case, the declaration in the output document is redundant.

These unwanted declarations are mostly harmless, however they are a source of unnecessary document bloat and can interfere with validation.

Scenario

Suppose you have the following XSLT stylesheet, which reduces an Atom feed into a series of HTML-style hyperlinks:

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

<xsl:template match="/atom:feed">
 <links><xsl:apply-templates select="//atom:entry"/></links>
</xsl:template>

<xsl:template match="atom:entry">
 <a><xsl:attribute name="href"><xsl:value-of select="atom:link/@href"/></xsl:attribute>
  <xsl:value-of select="atom:title/text()"/>
 </a>
</xsl:template>
</xsl:stylesheet>

The Atom namespace (http://www.w3.org/2005/Atom) is used within this stylesheet, but only for the purpose of recognising the elements atom::feed, atom:entry, atom:link and atom:title in the input document. There is no need for the declaration to be copied into the output document, but it will appear there if the stylesheet is used as it stands:

<?xml version="1.0" encoding="UTF-8"?>
<links xmlns:atom="http://www.w3.org/2005/Atom">
 <!-- ... -->
</links>

Method

Add an exclude-result-prefixes attribute to the stylesheet element. This should contain a space-separated list of namespace prefixes that you do not want to be declared in the output document, for example:


<xsl:stylesheet version="1.0"
 xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
 xmlns:atom="http://www.w3.org/2005/Atom"
 exclude-result-prefixes="atom">

If you make this change to the stylesheet listed above then link element in the output document should cease to have an xmlns:atom attribute:

<?xml version="1.0" encoding="UTF-8"?>
<links>
 <!-- ... -->
</links>

The XSLT namespace (http://www.w3.org/1999/XSL/Transform) is automatically excluded, therefore it is not necessary to list the corresponding prefix (normally xsl).

Tags: xslt