xsl subsets of nodesets

W

will

HOpe you can help with this...

I have the following xml document...

<?xml version="1.0" ?>
<file>
<header>some data</header>
<detail> some more data</detail>
<footer> gdshada </footer>

<header>some data</header>
<detail> some more data</detail>
<detail> some more data</detail>
<detail> some more data</detail>
<footer> gdshada </footer>

<header>some data</header>
<detail> some more data</detail>
<detail> some more data</detail>
<footer> gdshada </footer>
</file>


I am using xslt to process these header detail records.
The question is how can i select the subsets of detail tags in turn
for processing as they are on the same level in terms of hierachy

I would maybe like to do something similar to ..

<xsl:for-each select="following::DETAIL[position() &gt;=
$header_position and position() &lt;= $footer_position]">

.... but how can i determine the header and footer position?

Thanks for any help..

Will
 
M

Marrow

Hi Will,

So you can see which <detail> and <footer> elements are getting pushed....

== XML ==========================================
<?xml version="1.0"?>
<file>
<header>h1</header>
<detail>d1</detail>
<footer>f1</footer>

<header>h2</header>
<detail>d2.1</detail>
<detail>d2.2</detail>
<detail>d2.3</detail>
<footer>f2</footer>

<header>h3</header>
<detail>d3.1</detail>
<detail>d3.2</detail>
<footer>f3</footer>
</file>
== end of XML ===================================

Try something like...

== XSL ==========================================
<?xml version="1.0"?>
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:eek:utput method="html" indent="yes"/>
<xsl:template match="file">
<html>
<body>
<xsl:apply-templates select="header"/>
</body>
</html>
</xsl:template>

<xsl:template match="header">
<h3>
<xsl:value-of select="."/>
</h3>
<!-- apply to all details and footers that follow this header -->
<xsl:apply-templates select="(following-sibling::detail |
following-sibling::footer)[generate-id(preceding-sibling::header[1]) =
generate-id(current())]"/>
</xsl:template>

<xsl:template match="detail">
<div>
<xsl:value-of select="."/>
</div>
</xsl:template>

<xsl:template match="footer">
<div style="font-style: italic; font-size: small;">
<xsl:text>(footer: </xsl:text>
<xsl:value-of select="."/>
<xsl:text>)</xsl:text>
</div>
</xsl:template>
</xsl:stylesheet>
== end of XSL ===================================

Hope this helps
Marrow
http://www.marrowsoft.com - home of Xselerator (XSLT IDE and debugger)
http://www.topxml.com/Xselerator
 
W

will

That looks pretty good thanks marrow, but it needs to be taken a bit
further

I need to pass the name of the header into its corresponding details
somehow. So for the xml/xslt you describe below we could have the
following result...

<html>
<body>
<h3>header1</h3>
<div>detail 1 belongs to header 1</div>
<div style="font-style: italic; font-size: small;">(footer:
f1)</div>
<h3>header2</h3>
<div>detail 1 belongs to header 2</div>
<div>detail 2 belongs to header 2</div>
<div>detail 3 belongs to header 2</div>
<div style="font-style: italic; font-size: small;">(footer:
f2)</div>
<h3>header3</h3>
<div>detail 1 belongs to header 3</div>
<div>detail 2 belongs to header 3</div>
<div style="font-style: italic; font-size: small;">(footer:
f3)</div>
</body>
</html>


with the detail tags saying which header they "belong" to..

thanks agian for your help..


Marrow said:
Hi Will,

So you can see which <detail> and <footer> elements are getting pushed....

== XML ==========================================
<?xml version="1.0"?>
<file>
<header>h1</header>
<detail>d1</detail>
<footer>f1</footer>

<header>h2</header>
<detail>d2.1</detail>
<detail>d2.2</detail>
<detail>d2.3</detail>
<footer>f2</footer>

<header>h3</header>
<detail>d3.1</detail>
<detail>d3.2</detail>
<footer>f3</footer>
</file>
== end of XML ===================================

Try something like...

== XSL ==========================================
<?xml version="1.0"?>
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:eek:utput method="html" indent="yes"/>
<xsl:template match="file">
<html>
<body>
<xsl:apply-templates select="header"/>
</body>
</html>
</xsl:template>

<xsl:template match="header">
<h3>
<xsl:value-of select="."/>
</h3>
<!-- apply to all details and footers that follow this header -->
<xsl:apply-templates select="(following-sibling::detail |
following-sibling::footer)[generate-id(preceding-sibling::header[1]) =
generate-id(current())]"/>
</xsl:template>

<xsl:template match="detail">
<div>
<xsl:value-of select="."/>
</div>
</xsl:template>

<xsl:template match="footer">
<div style="font-style: italic; font-size: small;">
<xsl:text>(footer: </xsl:text>
<xsl:value-of select="."/>
<xsl:text>)</xsl:text>
</div>
</xsl:template>
</xsl:stylesheet>
== end of XSL ===================================

Hope this helps
Marrow
http://www.marrowsoft.com - home of Xselerator (XSLT IDE and debugger)
http://www.topxml.com/Xselerator



will said:
HOpe you can help with this...

I have the following xml document...

<?xml version="1.0" ?>
<file>
<header>some data</header>
<detail> some more data</detail>
<footer> gdshada </footer>

<header>some data</header>
<detail> some more data</detail>
<detail> some more data</detail>
<detail> some more data</detail>
<footer> gdshada </footer>

<header>some data</header>
<detail> some more data</detail>
<detail> some more data</detail>
<footer> gdshada </footer>
</file>


I am using xslt to process these header detail records.
The question is how can i select the subsets of detail tags in turn
for processing as they are on the same level in terms of hierachy

I would maybe like to do something similar to ..

<xsl:for-each select="following::DETAIL[position() &gt;=
$header_position and position() &lt;= $footer_position]">

... but how can i determine the header and footer position?

Thanks for any help..

Will
 
M

Marrow

Hi Will,

The easiest way would be pass the <header> node as param to the templates as
they are applied, e.g.

== XSL1 ==========================================
<?xml version="1.0"?>
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:eek:utput method="html" indent="yes"/>
<xsl:template match="file">
<html>
<body>
<xsl:apply-templates select="header"/>
</body>
</html>
</xsl:template>

<xsl:template match="header">
<h3>
<xsl:value-of select="."/>
</h3>
<!-- apply to all details and footers that follow this header -->
<xsl:apply-templates select="(following-sibling::detail |
following-sibling::footer)[generate-id(preceding-sibling::header[1]) =
generate-id(current())]">
<xsl:with-param name="hdr" select="."/>
</xsl:apply-templates>
</xsl:template>

<xsl:template match="detail">
<xsl:param name="hdr"/>
<div>
<xsl:value-of select="."/>
<xsl:text> belongs to </xsl:text>
<xsl:value-of select="$hdr"/>
</div>
</xsl:template>

<xsl:template match="footer">
<xsl:param name="hdr"/>
<div style="font-style: italic; font-size: small;">
<xsl:text>(footer: </xsl:text>
<xsl:value-of select="."/>
<xsl:text> belongs to </xsl:text>
<xsl:value-of select="$hdr"/>
<xsl:text>)</xsl:text>
</div>
</xsl:template>
</xsl:stylesheet>
== end of XSL1 ===================================

Alternatively you could always get hold of the preceding <header> for each
<detail> and <footer> quite easily, e.g.

== XSL2 ==========================================
<?xml version="1.0"?>
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:eek:utput method="html" indent="yes"/>
<xsl:template match="file">
<html>
<body>
<xsl:apply-templates select="header"/>
</body>
</html>
</xsl:template>

<xsl:template match="header">
<h3>
<xsl:value-of select="."/>
</h3>
<!-- apply to all details and footers that follow this header -->
<xsl:apply-templates select="(following-sibling::detail |
following-sibling::footer)[generate-id(preceding-sibling::header[1]) =
generate-id(current())]"/>
</xsl:template>

<xsl:template match="detail">
<div>
<xsl:value-of select="."/>
<xsl:text> belongs to </xsl:text>
<xsl:value-of select="preceding-sibling::header[1]"/>
</div>
</xsl:template>

<xsl:template match="footer">
<div style="font-style: italic; font-size: small;">
<xsl:text>(footer: </xsl:text>
<xsl:value-of select="."/>
<xsl:text> belongs to </xsl:text>
<xsl:value-of select="preceding-sibling::header[1]"/>
<xsl:text>)</xsl:text>
</div>
</xsl:template>
</xsl:stylesheet>
== end of XSL2 ===================================


Hope this helps
Marrow
http://www.marrowsoft.com - home of Xselerator (XSLT IDE and debugger)
http://www.topxml.com/Xselerator


will said:
That looks pretty good thanks marrow, but it needs to be taken a bit
further

I need to pass the name of the header into its corresponding details
somehow. So for the xml/xslt you describe below we could have the
following result...

<html>
<body>
<h3>header1</h3>
<div>detail 1 belongs to header 1</div>
<div style="font-style: italic; font-size: small;">(footer:
f1)</div>
<h3>header2</h3>
<div>detail 1 belongs to header 2</div>
<div>detail 2 belongs to header 2</div>
<div>detail 3 belongs to header 2</div>
<div style="font-style: italic; font-size: small;">(footer:
f2)</div>
<h3>header3</h3>
<div>detail 1 belongs to header 3</div>
<div>detail 2 belongs to header 3</div>
<div style="font-style: italic; font-size: small;">(footer:
f3)</div>
</body>
</html>


with the detail tags saying which header they "belong" to..

thanks agian for your help..


"Marrow" <[email protected]> wrote in message
Hi Will,

So you can see which <detail> and <footer> elements are getting pushed....

== XML ==========================================
<?xml version="1.0"?>
<file>
<header>h1</header>
<detail>d1</detail>
<footer>f1</footer>

<header>h2</header>
<detail>d2.1</detail>
<detail>d2.2</detail>
<detail>d2.3</detail>
<footer>f2</footer>

<header>h3</header>
<detail>d3.1</detail>
<detail>d3.2</detail>
<footer>f3</footer>
</file>
== end of XML ===================================

Try something like...

== XSL ==========================================
<?xml version="1.0"?>
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:eek:utput method="html" indent="yes"/>
<xsl:template match="file">
<html>
<body>
<xsl:apply-templates select="header"/>
</body>
</html>
</xsl:template>

<xsl:template match="header">
<h3>
<xsl:value-of select="."/>
</h3>
<!-- apply to all details and footers that follow this header -->
<xsl:apply-templates select="(following-sibling::detail |
following-sibling::footer)[generate-id(preceding-sibling::header[1]) =
generate-id(current())]"/>
</xsl:template>

<xsl:template match="detail">
<div>
<xsl:value-of select="."/>
</div>
</xsl:template>

<xsl:template match="footer">
<div style="font-style: italic; font-size: small;">
<xsl:text>(footer: </xsl:text>
<xsl:value-of select="."/>
<xsl:text>)</xsl:text>
</div>
</xsl:template>
</xsl:stylesheet>
== end of XSL ===================================

Hope this helps
Marrow
http://www.marrowsoft.com - home of Xselerator (XSLT IDE and debugger)
http://www.topxml.com/Xselerator



will said:
HOpe you can help with this...

I have the following xml document...

<?xml version="1.0" ?>
<file>
<header>some data</header>
<detail> some more data</detail>
<footer> gdshada </footer>

<header>some data</header>
<detail> some more data</detail>
<detail> some more data</detail>
<detail> some more data</detail>
<footer> gdshada </footer>

<header>some data</header>
<detail> some more data</detail>
<detail> some more data</detail>
<footer> gdshada </footer>
</file>


I am using xslt to process these header detail records.
The question is how can i select the subsets of detail tags in turn
for processing as they are on the same level in terms of hierachy

I would maybe like to do something similar to ..

<xsl:for-each select="following::DETAIL[position() &gt;=
$header_position and position() &lt;= $footer_position]">

... but how can i determine the header and footer position?

Thanks for any help..

Will
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,769
Messages
2,569,582
Members
45,057
Latest member
KetoBeezACVGummies

Latest Threads

Top