Altova Mailing List Archives>Archive Index >microsoft.public.xml Archive Home >Recent entries >Thread Prev - Re: xslt and multiple tables >Thread Next - Re: xslt and multiple tables Re: xslt and multiple tablesTo: NULL Date: 1/10/2008 9:14:00 AM
"tshad" <tshad@d...> wrote in message
news:eFirJQxUIHA.5980@T......
>
> "Anthony Jones" <Ant@y...> wrote in message
> news:uvHKtpwUIHA.4696@T......
> > "tshad" <tfs@d...> wrote in message
> > news:%23lSV32oUIHA.5496@T......
> >>
> >> "Anthony Jones" <Ant@y...> wrote in message
> >> news:u3BzqjeUIHA.5836@T......
> >> > "tshad" <tfs@d...> wrote in message
> >> > news:uFuhAIbUIHA.5404@T......
> >> >> I have an xml file and xslt file that worked fine together until I
> > added
> >> >> another set of tags (analysis).
> >> >>
> >> >> <?xml version="1.0"?>
> >> >> <addresses>
> >> >> <address>
> >> >> <tag name="street">One Microsoft Way</tag>
> >> >> </address>
> >> >> <address>
> >> >> <section Comp="1">
> >> >> <tag name="street">15 Mako Place</tag>
> >> >> </section>
> >> >> </address>
> >> >> <analysis >
> >> >> <files>
> >> >> <rulefile>
> >> >> <version>09282007</version>
> >> >> <name>March Errors</name>
> >> >> </rulefile>
> >> >> </files>
> >> >> </analysis>
> >> >> </addresses>
> >> >>
> >> >> The xslt file is:
> >> >>
> >> >> <xsl:stylesheet version="1.0"
> >> >> xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
> >> >>
> >> >> xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
> >> >> <xsl:output method="xml" indent="yes"/>
> >> >> <xsl:template match="address">
> >> >> <dataset>
> >> >> <xsl:apply-templates/>
> >> >> </dataset>
> >> >> </xsl:template>
> >> >> <xsl:template match="tag|section/tag">
> >> >> <address>
> >> >> <sectionNumber>
> >> >> <xsl:value-of select="ancestor::section/@Comp"/>
> >> >> </sectionNumber>
> >> >> <name>
> >> >> <xsl:value-of select="@name"/>
> >> >> </name>
> >> >> <value>
> >> >> <xsl:value-of select="."/>
> >> >> </value>
> >> >> </address>
> >> >> </xsl:template>
> >> >> </xsl:stylesheet>
> >> >>
> >> >> But the result file is:
> >> >>
> >> >> <?xml version="1.0" encoding="IBM437"?>
> >> >> <dataset xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
> >> >>
> >> >>
> >> > <address><sectionNumber></sectionNumber><name>street</name><flag
> >> >> xsi:nil="true"></flag><unit xsi:nil="true"></unit><value>One
> >> >> Microsoft
> >> >> Way</val
> >> >> ue></address>
> >> >>
> >> >>
> >> >>
> >> >>
> >> > <address><sectionNumber>1</sectionNumber><name>street</name><fla
> >> >> g xsi:nil="true"></flag><unit xsi:nil="true"></unit><value>15 Mako
> >> >> Place</value>
> >> >> </address>
> >> >>
> >> >>
> >> >>
> >> >>
> >> >>
> >> >> 09282007
> >> >> March Errors
> >> >>
> >> >>
> >> >>
> >> >> </dataset>
> >> >>
> >> >> Not sure why I have all the blank lines but you will notice that all
> > the
> >> >> tags after the 2nd "address" are gone.
> >> >>
> >> >> There are no tags around the "09282007" and "March Errors".
> >> >>
> >> >> What I am trying to do is set this up so that I will end up with 2
> > tables
> >> > in
> >> >> a dataset that will read this result - an "address" table and an
> >> > "analysis"
> >> >> table.
> >> >>
> >> >> How would I change my xlst file to do this?
> >> >>
> >> >
> >> > Try this:-
> >> >
> >> > <xsl:template match="/addresses">
> >> > <dataset>
> >> > <xsl:apply-templates select="address" />
> >> > </dataset>
> >> > </xsl:template>
> >> >
> >> > Its usually a good idea to make sure your first template matches the
> >> > document root element and if possible use an explicit select on
> >> > apply-templates.
> >> >
> >>
> >> That works but just drops the analysis section (although it does get
rid
> > of
> >> the text from that section that was being displayed. What I was using
> > was:
> >>
> >> <xsl:stylesheet version="1.0"
> >> xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
> >> xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
> >> <xsl:output method="xml" indent="yes"/>
> >> <xsl:template match="addresses">
> >> <dataset>
> >> <xsl:apply-templates select="address"/>
> >> </dataset>
> >> </xsl:template>
> >> <xsl:template match="tag|section/tag">
> >> <address>
> >> <sectionNumber>
> >> <xsl:value-of select="ancestor::section/@Comp"/>
> >> </sectionNumber>
> >> <name>
> >> <xsl:value-of select="@name"/>
> >> </name>
> >> <value>
> >> <xsl:value-of select="."/>
> >> </value>
> >> </address>
> >> </xsl:template>
> >> </xsl:stylesheet>
> >>
> >>
> >> I assume that if I want to use the analysis section I would need to do
> >> something like:
> >>
> >> <dataset>
> >> <xsl:apply-templates select="address"/>
> >> <xsl:apply-templates select="analysis"/>
> >> </dataset>
> >>
> >> Then I would need to set up some type of match for the analysis section
> > but
> >> how does the xsl know which match to use with which select?
> >>
> >
> >
> > It doesn't. It tries to apply all nodes returned by the select to all
of
> > the templates. However only one of the templates will get used and that
> > will
> > be the one which is the best match for the node. If no template matches
> > at
> > all then the builtin default one is used.
> >
> > In your case you would create a new template:-
> >
> > <xsl:template match="analysis">
> > . . .
> > </xsl:template>
> >
> Sorry about the other post.
>
> I tried something like what you had and almost have it. I changed the
match
> to be analysis/files/rulefile/version and it works for the version but not
> the created a whole other row.
>
> I modified the xml slightly to add an attribute and it looks like:
>
> <?xml version="1.0"?>
> <addresses>
> <address>
> <tag name="street">One Microsoft Way</tag>
> </address>
> <address>
> <section Comp="1">
> <tag name="street">15 Mako Place</tag>
> </section>
> </address>
> <analysis >
> <files>
> <rulefile>
> <version form="text">09282007</version>
> <name>March Errors</name>
> </rulefile>
> </files>
> </analysis>
> </addresses>
>
> My xsl file is:
>
> <xsl:stylesheet version="1.0"
> xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
> xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
> <xsl:output method="xml" indent="yes"/>
> <xsl:template match="addresses">
> <dataset>
> <xsl:apply-templates select="*"/>
> </dataset>
> </xsl:template>
> <xsl:template match="tag|section/tag">
> <address>
> <sectionNumber>
> <xsl:value-of select="ancestor::section/@Comp"/>
> </sectionNumber>
> <name>
> <xsl:value-of select="@name"/>
> </name>
> <flag>
> <xsl:if test="not(@flag)">
> <xsl:attribute name="xsi:nil">true</xsl:attribute>
> </xsl:if>
> <xsl:value-of select="@flag"/>
> </flag>
> <unit>
> <xsl:if test="not(@unit)">
> <xsl:attribute name="xsi:nil">true</xsl:attribute>
> </xsl:if>
> <xsl:value-of select="@unit"/>
> </unit>
> <value>
> <xsl:value-of select="."/>
> </value>
> </address>
> </xsl:template>
> <xsl:template match="analysis/files/rulefile/version">
> <analysis>
> <form>
> <xsl:value-of select="@form"/>
> </form>
> <value>
> <xsl:value-of select="."/>
> </value>
> <name>
> <xsl:value-of select="following-sibling::name/text()"/>
> </name>
> </analysis>
> </xsl:template>
> </xsl:stylesheet>
>
> I am getting the following:
>
> <?xml version="1.0" encoding="IBM437"?>
> <dataset xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
> <address><sectionNumber></sectionNumber><name>street</name><flag
> xsi:nil="true"></flag><unit xsi:nil="true"></unit><value>One Microsoft
> Way</val
> ue></address>
>
>
> <address><sectionNumber>1</sectionNumber><name>street</name><fla
> g xsi:nil="true"></flag><unit xsi:nil="true"></unit><value>15 Mako
> Place</value>
> </address>
>
>
> <analysis><form>text</form><value>09282007</value><name>March
> Errors</name></analysis>
> March Errors
>
>
> </dataset>
>
> Why am I getting the extra "March Errors"? I also tried:
>
> <name>
> <xsl:value-of select="following-sibling::name/.>
> </name>
>
> and got the same result.
>
> The line before it is exactly what I am trying to get which will be 1 row
> with 3 columns (form,value,name).
>
You've managed again to have a node that doesn't match any template
therefore gets the default treatment.
analysis/files/rulefile/name doesn't match a template and therefore its text
gets dumped into the output.
The anaylsis template would be simpler as:-
<xsl:template match="analysis/files/rulefile">
<analysis>
<form>
<xsl:value-of select="version/@form"/>
</form>
<value>
<xsl:value-of select="version"/>
</value>
<name>
<xsl:value-of select="name"/>
</name>
</analysis>
</xsl:template>
This would eliminate the unwanted output and is easier to understand.
BTW select="*" on apply-templates is effectively the same as not having a
select at all. Using more explicit selects like select="address" allows you
to take control of the output documents element ordering. (E.g., if the
input document had further address elements following the analysis element
select="*" would just output the elements in the order they appeared in the
input whereas select="address" would group all the address elements
together.)
Also match="tag|section/tag" might as well be match="tag".
--
Anthony Jones - MVP ASP/ASP.NET
| ||||||
| Company | Legal | Press | Partners | Careers | Sitemap | Contact Us | Altova Blog | Mobile | Full Site | |||
|
