开发者

xsl:include template with no default namespace causes xmlns=""

I've got a problem with xsl:include and default namespaces which is causing the final xml document contain nodes with the xmlns=""

In this synario I have 1 source document which is Plain Old XML and doesn't have a namespace:

<?xml version="1.0" encoding="UTF-8"?>
<SourceDoc>
    <Description>Hel开发者_开发问答lo I'm the source description</Description>
    <Description>Hello I'm the source description 2</Description>
    <Description/>
    <Title>Hello I'm the title</Title>
</SourceDoc>

This document is transformed into 2 different xml documents each with their own default namespace.

First Document:

<?xml version="1.0" encoding="utf-8"?>
<OutputDocType1 xmlns="http://MadeupNS1">
   <Description >Hello I'm the source description</Description>
   <Description>Hello I'm the source description 2</Description>
   <Title>Hello I'm the title</Title>
</OutputDocType1>

Second Document:

<?xml version="1.0" encoding="utf-8"?>
<OutputDocType2 xmlns="http://MadeupNS2">
   <Description>Hello I'm the source description</Description>
   <Description>Hello I'm the source description 2</Description>
   <DocTitle>Hello I'm the title</DocTitle>
</OutputDocType2>

I want to be able to re-use the template for descriptions in both of the transforms. As it's the same logic for both types of document. To do this I created a template file which was xsl:included in the other 2 transformations:

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

    <xsl:output indent="yes" method="xml"/>

    <xsl:template match="Description[. != '']">
        <Description>
            <xsl:value-of select="."/>
        </Description>
    </xsl:template>
</xsl:stylesheet>

Now the problem here is that this shared transformation can't have a default Namespace as it will be different depending on which of the calling transformations calls it.

E.g. for First Document Transformation:

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

    <xsl:output indent="yes" method="xml"/>
    <xsl:template match="SourceDoc">
        <OutputDocType1 xmlns="http://MadeupNS1">

            <xsl:apply-templates select="Description"/>
            <xsl:if test="Title">
                <Title>
                    <xsl:value-of select="Title"/>
                </Title>
            </xsl:if>
        </OutputDocType1>
    </xsl:template>

    <xsl:include href="Template.xsl"/>
</xsl:stylesheet>

This actually outputs it as follows:

<?xml version="1.0" encoding="utf-8"?>
<OutputDocType1 xmlns="http://MadeupNS1">
   <Description xmlns="">Hello I'm the source description</Description>
   <Description xmlns="">Hello I'm the source description 2</Description>
   <Title>Hello I'm the title</Title>
</OutputDocType1>

Here is the problem. On the description Lines I get an xmlns=""

Does anyone know how to solve this issue?

Thanks

Dave


Your first xslt, which contains the literal result element Description has no default namespace. This element is therefore in no namespace, and is being explicitly rendered as such via xmlns="".

Section 6.2 of Namespaces in XML 1.0 says that:

The attribute value in a default namespace declaration MAY be empty. This has the same effect, within the scope of the declaration, of there being no default namespace.

In order to control the namespace generated in the included stylesheet you will need to pass the namespace-uri through to its templates, using a variable or param.

<!-- in the included stylesheet -->
<xsl:template match="Description[. != '']">
    <xsl:element name="Description" namespace="{$output-namespace}">
        <xsl:value-of select="."/>
    </xsl:element>
</xsl:template>

<!--
    and add this to your First Document Transformation stylesheet
    as a top level element under xsl:stylesheet
-->
<xsl:variable name="output-namespace" select="'http://MadeupNS1'"/>
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜