Wrox Programmer Forums
Go Back   Wrox Programmer Forums > XML > XSLT
|
XSLT General questions and answers about XSLT. For issues strictly specific to the book XSLT 1.1 Programmers Reference, please post to that forum instead.
Welcome to the p2p.wrox.com Forums.

You are currently viewing the XSLT section of the Wrox Programmer to Programmer discussions. This is a community of software programmers and website developers including Wrox book authors and readers. New member registration was closed in 2019. New posts were shut off and the site was archived into this static format as of October 1, 2020. If you require technical support for a Wrox book please contact http://hub.wiley.com
 
Old September 18th, 2012, 01:43 AM
Authorized User
 
Join Date: Jul 2010
Posts: 74
Thanks: 23
Thanked 0 Times in 0 Posts
Question How to remove the father element if the child elements are empty

There are several loop father nodes which contain several child elements, like below:
Quote:
<?xml version="1.0" encoding="utf-8" ?>
<ns0:PO xmlns:ns0="http://HelloWorld.POSchema">
<PO_Number>16</PO_Number>
<Total>PO_Number1234</Total>
<PO_Number2>6</PO_Number2>
<PO_Number3>5</PO_Number3>
<PORoot>
<PORoot1>PORoot1</PORoot1>
<PORoot2>PORoot2</PORoot2>
<POChild>
<POChild1>POChild1</POChild1>
<POChild2>POChild2</POChild2>
</POChild>
<PORoot1>PORoot3</PORoot1>
<PORoot2>PORoot4</PORoot2>
<POChild>
<POChild1>POChild3</POChild1>
<POChild2></POChild2>
</POChild>
<PORoot1>PORoot5</PORoot1>
<PORoot2>PORoot6</PORoot2>
<POChild>
<POChild1></POChild1>
<POChild2></POChild2>
</POChild>
<PORoot1></PORoot1>
<PORoot2></PORoot2>
<POChild>
<POChild1></POChild1>
<POChild2></POChild2>
</POChild>
</PORoot>
</ns0:PO>
What I want to do is that I want to remove all the empty POChild nodes, if the two child POChild1/2 nodes are empty, remove the father node POChild as well.

I have no idea how to achive this.

The output xml should be like below, but probably a little different:
Code:
<?xml version="1.0" encoding="utf-8" ?>
<PO>
  <PO_Number>16</PO_Number>
  <Total>PO_Number1234</Total>
  <PO_Number2>6</PO_Number2>
  <PO_Number3>5</PO_Number3>
  <PORoot>
    <PORoot1>PORoot1</PORoot1>
    <PORoot2>PORoot2</PORoot2>
    <POChild>
      <POChild1>POChild1</POChild1>
      <POChild2>POChild2</POChild2>
    </POChild>
    <PORoot1>PORoot3</PORoot1>
    <PORoot2>PORoot4</PORoot2>
    <POChild>
      <POChild1>POChild3</POChild1>
    </POChild>
    <PORoot1>PORoot5</PORoot1>
    <PORoot2>PORoot6</PORoot2>
  </PORoot>
</PO>

ATTENTION: The first node is ns0:PO with xmlns.

Thank you so much in advance!

Last edited by JohnKiller; September 18th, 2012 at 01:50 AM..
 
Old September 18th, 2012, 04:45 AM
mhkay's Avatar
Wrox Author
 
Join Date: Apr 2004
Posts: 4,962
Thanks: 0
Thanked 292 Times in 287 Posts
Default

You want a transformation that defines an identity rule to copy elements by default:

Code:
<xsl:template match="*">
  <xsl:copy><xsl:apply-templates/></xsl:copy>
</xsl:template>
and then rules to avoid copying POChild, POChild1, and POChild2 elements if they have no text content:

Code:
<xsl:template match="n:POChild[not(normalize-space())]"/>
<xsl:template match="n:POChild1[not(normalize-space())]"/>
<xsl:template match="n:POChild2[not(normalize-space())]"/>
The namespace prefix "n" should be bound to the right namespace by adding

xmlns:n="http://HelloWorld.POSchema"

to your xsl:stylesheet element. Of course you can use a different namespace prefix if you prefer.
__________________
Michael Kay
http://www.saxonica.com/
Author, XSLT 2.0 and XPath 2.0 Programmer\'s Reference
The Following User Says Thank You to mhkay For This Useful Post:
JohnKiller (September 18th, 2012)
 
Old September 18th, 2012, 06:13 AM
Authorized User
 
Join Date: Jul 2010
Posts: 74
Thanks: 23
Thanked 0 Times in 0 Posts
Default

Hello Michael,
Thank you for your reply.
Is there any way to put them in one template, like we deal with the node without namespace? <xsl:template match="PO">
 
Old September 18th, 2012, 06:24 AM
mhkay's Avatar
Wrox Author
 
Join Date: Apr 2004
Posts: 4,962
Thanks: 0
Thanked 292 Times in 287 Posts
Default

Why on earth would you want to put code in a single template when it can be broken up cleanly into several independent templates?
__________________
Michael Kay
http://www.saxonica.com/
Author, XSLT 2.0 and XPath 2.0 Programmer\'s Reference
 
Old September 18th, 2012, 06:30 AM
Authorized User
 
Join Date: Jul 2010
Posts: 74
Thanks: 23
Thanked 0 Times in 0 Posts
Default

Since I really do not know how to assemble all the templates together, and the relationships among them. The material which I found online make me confusing. And when I tested the templates, it cannot work right.
 
Old September 18th, 2012, 04:24 PM
mhkay's Avatar
Wrox Author
 
Join Date: Apr 2004
Posts: 4,962
Thanks: 0
Thanked 292 Times in 287 Posts
Default

>The material which I found online make me confusing

Did you know that Wrox publishes books on XML, and that this forum is primarily intended for readers of those books?

If you're not used to learning from books, I can really recommend it. Unlike most online resources, books are carefully designed, written, edited, and proofread, and Wrox has a high reputation for the quality of the reviewers who ensure that the material is consistent, correct, and well-presented.
__________________
Michael Kay
http://www.saxonica.com/
Author, XSLT 2.0 and XPath 2.0 Programmer\'s Reference
 
Old September 18th, 2012, 07:40 PM
Authorized User
 
Join Date: Jul 2010
Posts: 74
Thanks: 23
Thanked 0 Times in 0 Posts
Default

Sound great! Yes, I have several Wrox books, but no one is related to XML and XSLT.

I searched Wrox Bookstore/E-Books, there are a lot of books related to XML and XSLT. Would you give me recommendation which book is better?

Thank you!
 
Old October 18th, 2012, 09:50 AM
Registered User
 
Join Date: Oct 2012
Posts: 3
Thanks: 0
Thanked 0 Times in 0 Posts
Default Solution

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="2.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:ns0="http://HelloWorld.POSchema">
<xsl:output method="xml"/>
<xsl:template match="/">
<xsl:apply-templates select="ns0:PO"/>
</xsl:template>
<xsl:template match="ns0:PO">
<xsl:element name="PO">
<xsl:copy-of select="child::* except PORoot" copy-namespaces="no"/>
<xsl:apply-templates select="PORoot"/>
</xsl:element>
</xsl:template>
<xsl:template match="PORoot">
<xsl:element name="PORoot">
<xsl:apply-templates/>
</xsl:element>
</xsl:template>
<xsl:template match="POChild">
<xsl:if test="child::* and child::*[text()!=' ']">
<xsl:element name="POChild">
<xsl:for-each select="child::*">
<xsl:if test="text()!= ' '">
<xsl:copy-of select="." copy-namespaces="no"/>
</xsl:if>
</xsl:for-each>
</xsl:element>
</xsl:if>
</xsl:template>
<xsl:template match="PORoot1">
<xsl:if test="text()!=' '">
<xsl:element name="PORoot1">
<xsl:value-of select="."/>
</xsl:element>
</xsl:if>
</xsl:template>

<xsl:template match="PORoot2">
<xsl:if test="text()!=' '">
<xsl:element name="PORoot2">
<xsl:value-of select="."/>
</xsl:element>
</xsl:if>
</xsl:template>
</xsl:stylesheet>





Similar Threads
Thread Thread Starter Forum Replies Last Post
Change ALL DateTime Child Elements BobSSC XSLT 2 February 18th, 2010 01:28 PM
Finding the first child element humansky XSLT 5 April 17th, 2008 08:46 AM
Checking for valid child elements. Chamkaur XSLT 0 January 25th, 2007 06:51 PM
Access specific Element and its Child elements! suersh79 XML 3 November 22nd, 2006 12:58 AM
child element kgoldvas XML 4 April 27th, 2006 01:51 AM





Powered by vBulletin®
Copyright ©2000 - 2020, Jelsoft Enterprises Ltd.
Copyright (c) 2020 John Wiley & Sons, Inc.