Namspaceノードは、XSLTの使用するツリーモデルのXDM ()によれば次のように解説されています.
6.4 Namespace Nodes
Each Namespace Node represents the binding of a namespace URI to a namespace prefix or to the default namespace.
では実際にテンプレートでこれを出してみようとするとうまくゆきません.なぜかと言うと
<xsl:apply-templates select="namespace::node()"/>
と書いてもエラーになりませんが、受け手を
<xsl:template match="namespace::node()">
と書くとXSLT 2.0ではエラーになってしまうからです.そうです、match属性に書くパターンにはnamespace軸は書けないのです.
そこで唯一の手段は次のようなコードを書くことになります.
<xsl:for-each select="namespace::node()">
<node>
<xsl:attribute name="node-type">namespace</xsl:attribute>
<xsl:variable name="nsNode" select="."/>
<xsl:attribute name="name"><xsl:value-of select="name()"/></xsl:attribute>
<xsl:value-of select="string(.)"/>
</node>
</xsl:for-each>
こうした場合の出力は次のようになります.要素毎にnamespaceノードがあって、確かにネームスペースURIとネームスペースプレフィックスの関係を保持していてくれることがわかります."xml"という接頭辞はxml:spaceやxsl:langを書くときに使うのですね.
<root>
<node node-type="document-node">
Document title
The quick brown fox jumps over the lazy dog
</node>
<node node-type="element" name="doc">
<node node-type="namespace" name="xml">http://www.w3.org/XML/1998/namespace</node>
Document title
The quick brown fox jumps over the lazy dog
</node>
<node node-type="text">
</node>
<node node-type="element" name="title">
<node node-type="namespace" name="xml">http://www.w3.org/XML/1998/namespace</node>Document title</node>
<node node-type="text">Document title</node>
<node node-type="text">
</node>
<node node-type="element" name="chapter">
<node node-type="namespace" name="xml">http://www.w3.org/XML/1998/namespace</node>
<node node-type="attribute" name="toc">yes</node>
The quick brown fox jumps over the lazy dog
</node>
<node node-type="text">
</node>
<node node-type="comment"> これはコメントです</node>
<node node-type="text">
</node>
<node node-type="processing-instruction" name="pi">これは処理命令です.</node>
<node node-type="text">
</node>
<node node-type="element"
namespace-uri="urn:x-antennahouse-1"
local-name="p">
<node node-type="namespace" name="ah1">urn:x-antennahouse-1</node>
<node node-type="namespace" name="ah2">urn:x-antennahouse-2</node>
<node node-type="namespace" name="xml">http://www.w3.org/XML/1998/namespace</node>
<node node-type="attribute"
namespace-uri="urn:x-antennahouse-2"
local-name="break-before">page</node>The quick brown fox jumps over the lazy dog</node>
<node node-type="text">The quick brown fox jumps over the lazy dog</node>
<node node-type="text">
</node>
<node node-type="text">
</node>
</root>
最終的なスタイルシートは次のようになりました.
<xsl:stylesheet version="2.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
exclude-result-prefixes="xs"
>
<xsl:output indent="yes"/>
<xsl:template match="/">
<root>
<xsl:call-template name="process-node"/>
</root>
</xsl:template>
<xsl:template match="child::node()|attribute::node()" name="process-node">
<node>
<xsl:attribute name="node-type">
<xsl:choose>
<xsl:when test="self::document-node()">document-node</xsl:when>
<xsl:when test="self::element()">element</xsl:when>
<xsl:when test="self::attribute()">attribute</xsl:when>
<xsl:when test="self::text()">text</xsl:when>
<xsl:when test="self::comment()">comment</xsl:when>
<xsl:when test="self::processing-instruction()">processing-instruction</xsl:when>
<xsl:otherwise/>
</xsl:choose>
</xsl:attribute>
<xsl:choose>
<xsl:when test="string(namespace-uri())">
<xsl:attribute name="local-name" select="local-name()"/>
</xsl:when>
<xsl:when test="string(name())">
<xsl:attribute name="name" select="name()"/>
</xsl:when>
<xsl:otherwise/>
</xsl:choose>
<xsl:for-each select="namespace::node()">
<node>
<xsl:attribute name="node-type">namespace</xsl:attribute>
<xsl:variable name="nsNode" as="node()" select="."/>
<xsl:attribute name="name"><xsl:value-of select="name()"/></xsl:attribute>
<xsl:value-of select="string(.)"/>
</node>
</xsl:for-each>
<xsl:apply-templates select="attribute::node()"/>
<xsl:value-of select="string(.)"/>
</node>
<xsl:apply-templates/>
</xsl:template>
</xsl:stylesheet>
oXygenはSaxon 9.5のXSLT 3.0(XPath 3.0)の実装が使えちゃいます.XSLTスタイルシートのバージョンを3.0にちょっと変えれば、スタイルシートは次のようにできます.これでまさしく、「すべてはノード」ということを理解していただけるのではないでしょうか?
<xsl:stylesheet version="3.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
exclude-result-prefixes="xs"
>
<xsl:output indent="yes"/>
<xsl:template match="/">
<root>
<xsl:call-template name="process-node"/>
</root>
</xsl:template>
<xsl:template match="child::node()|attribute::node()|namespace::node()" name="process-node">
<node>
<xsl:attribute name="node-type">
<xsl:choose>
<xsl:when test="self::document-node()">document-node</xsl:when>
<xsl:when test="self::element()">element</xsl:when>
<xsl:when test="self::namespace-node()">namespace</xsl:when>
<xsl:when test="self::attribute()">attribute</xsl:when>
<xsl:when test="self::text()">text</xsl:when>
<xsl:when test="self::comment()">comment</xsl:when>
<xsl:when test="self::processing-instruction()">processing-instruction</xsl:when>
<xsl:otherwise/>
</xsl:choose>
</xsl:attribute>
<xsl:choose>
<xsl:when test="string(namespace-uri())">
<xsl:attribute name="local-name" select="local-name()"/>
</xsl:when>
<xsl:when test="string(name())">
<xsl:attribute name="name" select="name()"/>
</xsl:when>
<xsl:otherwise/>
</xsl:choose>
<xsl:apply-templates select="namespace::node()"/>
<xsl:apply-templates select="attribute::node()"/>
<xsl:value-of select="string(.)"/>
</node>
<xsl:apply-templates/>
</xsl:template>
</xsl:stylesheet>
oXygenはSaxon9.5が使えるので、XSLT 3.0などいろいろ試してみるにはうってつけです.