Reputation: 15
I'm trying to remove empty elements within my XML document. I want id31, id32 and id33 removed when they are empty. Below is an example of the XSLT output. I'm trying to use the XSLT below but I'm not having any luck. Any ideas on what I'm doing wrong? Thanks
Data
<Item type="Part AML">
<related_id>
<Item type="Manufacturer Part">
<id keyed_name="1234" type="Manufacturer Part"></id>
<manufacturer keyed_name="Bobs Workshop" type="Manufacturer"></manufacturer>
<item_number>1234</item_number>
</Item>
</related_id>
</Item>
<Item type="Part Document">
<related_id keyed_name="D000005" type="Document">
<Item type="Document">
<id keyed_name="D000005" type="Document"></id>
<major_rev>B</major_rev>
<name>Firmware 8-16-12</name>
<item_number>D000005</item_number>
</Item>
</related_id>
</Item>
<Item type="Part Document">
<related_id keyed_name="D000003" type="Document">
<Item type="Document">
<id keyed_name="D000003" type="Document"></id>
<major_rev>A</major_rev>
<name>Design Spec</name>
<item_number>D000003</item_number>
</Item>
</related_id>
</Item>
Output
<td width="5%" align="center" uniqueID="ms__id31"></td>
<td width="13%" align="center" uniqueID="ms__id32"></td>
<td width="13%" align="center" uniqueID="ms__id33"></td>
<td width="5%" align="center" uniqueID="ms__id34">D000003</td>
<td width="13%" align="center" uniqueID="ms__id35">Design Spec</td>
<td width="8%" align="center" uniqueID="ms__id36">A</td>
Code from forums
<xsl:template match="node()|@*">
<xsl:copy>
<xsl:apply-templates select="node()|@*"/>
</xsl:copy>
</xsl:template>
<xsl:template match="*[not(@*|*|comment()|processing-instruction()) and normalize-space()='']"/>
My XSLT
<xsl:template match="Item[@type='Part AML']|Item[@type='Part Document']">
<tr>
<td width="5%" align="center" uniqueID="ms__id31">
<xsl:value-of select="state"/>
</td>
<td width="13%" align="center" uniqueID="ms__id32">
<xsl:value-of select="related_id[@type='Manufacturer Part']/Item/manufacturer/@keyed_name"/>
</td>
<td width="13%" align="center" uniqueID="ms__id33">
<xsl:value-of select="related_id[@type='Manufacturer Part']/Item/item_number"></xsl:value-of>
</td>
<td width="13%" align="center" uniqueID="ms__id34">
<xsl:value-of select="related_id[@type='Document']/Item/item_number"></xsl:value-of>
</td>
<td width="13%" align="center" uniqueID="ms__id35">
<xsl:value-of select="related_id[@type='Document']/Item/name"/>
</td>
<td width="8%" align="center" uniqueID="ms__id36">
<xsl:value-of select="related_id[@type='Document']/Item/major_rev"/>
</td>
</tr>
Upvotes: 0
Views: 409
Reputation: 11773
Use templates. This way, none are applied in the empty case:
<xsl:template match="Item[@type='Part AML']|Item[@type='Part Document']">
<tr>
<xsl:apply-templates select="state"/>
<xsl:apply-templates select="related_id[@type='Manufacturer Part']/Item/manufacturer/@keyed_name"/>
<xsl:apply-templates select="related_id[@type='Manufacturer Part']/Item/item_number">
<td width="13%" align="center" uniqueID="ms__id34">
<xsl:value-of select="related_id[@type='Document']/Item/item_number"></xsl:value-of>
</td>
<td width="13%" align="center" uniqueID="ms__id35">
<xsl:value-of select="related_id[@type='Document']/Item/name"/>
</td>
<td width="8%" align="center" uniqueID="ms__id36">
<xsl:value-of select="related_id[@type='Document']/Item/major_rev"/>
</td>
</tr>
</xsl:template>
<xsl:template match="Item[@type='Part AML' or @type='Part Document']/state">
<td width="5%" align="center" uniqueID="ms__id31">
<xsl:apply-templates>
</td>
</xsl:template>
<xsl:template match="Item[@type='Part AML' or @type='Part Document']/related_id[@type='Manufacturer Part']/Item/manufacturer/@keyed_name">
<td width="13%" align="center" uniqueID="ms__id32">
<xsl:apply-templates>
</td>
</xsl:template>
<xsl:template match="Item[@type='Part AML' or @type='Part Document']/related_id[@type='Manufacturer Part']/Item/item_number">
<td width="13%" align="center" uniqueID="ms__id33">
<xsl:apply-templates>
</td>
</xsl:template>
You can use the same pattern for the remaining <td>
s if they might have empty values too.
Upvotes: 1