help with html table (nested for-each/keys/matched template)

Discussion in 'XML' started by rick, Dec 18, 2005.

  1. rick

    rick Guest

    Greetings,

    I am trying to generate an html table that looks through the following
    xml source and lists links to all of the files (resource-file) and
    finds the resource-forms that match those file names and adds the
    appropriate file description next to the link to the filename. The xslt
    code that I've included doesn't work but gives an idea of what I'm
    trying to do. Through my research I believe that using keys and/or
    template matching my be the better way to go, but I'm not sure how to
    code them. I recognize that the xml structure is a little awkward but
    that's what I have to work with. Thanks in advance for any
    suggestions.

    Rick

    XML source

    <artifact>
    <resource-file>
    <artifact>
    <displayName>file1.doc</displayName>
    <uri>location of file1</uri>
    </artifact>
    <artifact>
    <displayName>file2.doc</displayName>
    <uri>location of file2</uri>
    </artifact>
    </resource-file>
    <resource-form>
    <file_name>file1.doc</file_name>
    <resource_description>file1.doc
    description</resource_description>
    </resource-form>
    <resource-form>
    <artifact>
    <file_name>file2.doc</file_name>
    <resource_description>file1.doc
    description</resource_description>
    </artifact>
    <artifact>
    <file_name>file3.doc</file_name>
    <resource_description>file3.doc
    description</resource_description>
    </artifact>
    <artifact>
    <file_name>file4.doc</file_name>
    <resource_description>file4.doc
    description</resource_description>
    </artifact>
    </resource-form>
    </artifact>

    Desired output

    Resource File(s) File Description
    (link to file1.doc) file1.doc description
    (link to file2.doc) file2.doc description

    nonworking xslt code

    <table>
    <tr>
    <td>Resource File(s)</td>
    <td>File Description</td>
    </tr>
    <tr>
    <xsl:for-each select="resource-file/artifact">
    <xsl:variable name="filename" select="metaData/displayName"/>
    <xsl:variable name="filelocation" select="fileArtifact/uri"/>
    <xsl:for-each select="resource-form/artifact"['file_name=$filename']>
    <tr>
    <td>
    <a>
    <xsl:attribute name="href">
    <xsl:value-of select="$filelocation"/>
    </xsl:attribute>
    <xsl:attribute name="target">blank</xsl:attribute>
    <xsl:value-of select="$filename"/>
    </a>
    </td>
    <td>
    <b>Resource Description:</b>
    <xsl:value-of
    select="structuredData/resource-form/resource_description"/>
    </td>
    </tr>
    </xsl:for-each>
    </xsl:for-each>
    </tr>
    </table>
     
    rick, Dec 18, 2005
    #1
    1. Advertising

  2. rick wrote:

    > code them. I recognize that the xml structure is a little awkward but
    > that's what I have to work with. Thanks in advance for any
    > suggestions.


    You dont need XSL for such a trivial data extraction.
    The following script in xmlgawk will do all the data
    extraction described:

    BEGIN { XMLMODE=1 }
    XMLCHARDATA { data = $0 }
    XMLENDELEM == "displayName" { name = data }
    XMLENDELEM == "uri" { uri[name] = data }
    XMLENDELEM == "resource_description" { split(data, d); dsc[d[1]] = data }

    END {
    for (n in uri) {
    print uri[n] "\t" n "\t" dsc[n]
    }
    }

    When running the script, you will get the result:

    gawk -lxml -f artifact.awk artifact.xml
    location of file1 file1.doc file1.doc
    description
    location of file2 file2.doc file2.doc
    description

    Notice the line break in the output, which are caused by
    your XML data. By the way, there is a bug in your XML data.

    > <artifact>
    > <file_name>file2.doc</file_name>
    > <resource_description>file1.doc

    here: ^^^^^^^^
    > description</resource_description>
    > </artifact>
     
    =?ISO-8859-1?Q?J=FCrgen_Kahrs?=, Dec 18, 2005
    #2
    1. Advertising

  3. rick

    Peter Flynn Guest

    rick wrote:

    > Greetings,
    >
    > I am trying to generate an html table that looks through the following
    > xml source and lists links to all of the files (resource-file) and
    > finds the resource-forms that match those file names and adds the
    > appropriate file description next to the link to the filename. The
    > xslt code that I've included doesn't work but gives an idea of what
    > I'm trying to do. Through my research I believe that using keys and/or
    > template matching my be the better way to go,


    Definitely. for-each is almost always the wrong answer :)

    > but I'm not sure how to
    > code them. I recognize that the xml structure is a little awkward but
    > that's what I have to work with.


    It would be useful -- both to you and your data-supplier -- to meet
    with a consultant to discuss improving the efficiency of the XML
    through redesigned document markup. The current design is seriously
    crippled by the fact that the resource-form element type can apparently
    contain either a single file_name/resource_description pair OR multiple
    occurrences of the artifact element type, and that the artifact element
    type has two apparently mutually exclusive content models, one for
    display_name and uri, and one for file_name and resource_description.
    Handling inconsistencies like this costs extra time and money, which
    you and/or your supplier can save by improving the data model.

    > Desired output
    >
    > Resource File(s) File Description
    > (link to file1.doc) file1.doc description
    > (link to file2.doc) file2.doc description


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

    <xsl:eek:utput method="html" indent="yes"/>
    <xsl:strip-space elements="*"/>

    <xsl:key name="description" match="resource_description"
    use="preceding-sibling::file_name"/>

    <xsl:template match="/">
    <table>
    <tr>
    <th>Resource File</th>
    <th>File Description</th>
    </tr>
    <xsl:apply-templates
    select="artifact/resource-file/artifact/displayName"/>
    </table>
    </xsl:template>

    <xsl:template match="displayName">
    <tr>
    <td>
    <a href="{following-sibling::uri}">
    <xsl:apply-templates/>
    </a>
    </td>
    <td>
    <xsl:value-of select="key('description',.)"/>
    </td>
    </tr>
    </xsl:template>

    </xsl:stylesheet>

    This produces:

    <table>
    <tr>
    <th>Resource File</th>
    <th>File Description</th>
    </tr>
    <tr>
    <td><a href="location of file1">file1.doc</a></td>
    <td>file1.doc description</td>
    </tr>
    <tr>
    <td><a href="location of file2">file2.doc</a></td>
    <td>file1.doc description</td>
    </tr>
    </table>

    ///Peter
    --
    XML FAQ: http://xml.silmaril.ie/
     
    Peter Flynn, Dec 18, 2005
    #3
    1. Advertising

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

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. sandeep Kanwal

    serial keys/validation keys

    sandeep Kanwal, Oct 29, 2004, in forum: C++
    Replies:
    1
    Views:
    585
    Mike Wahler
    Oct 29, 2004
  2. Replies:
    2
    Views:
    1,163
  3. Harry George
    Replies:
    9
    Views:
    707
    sonal
    Jun 13, 2006
  4. Replies:
    10
    Views:
    729
    Daniel T.
    Feb 3, 2006
  5. Replies:
    3
    Views:
    471
    Victor Bazarov
    Dec 7, 2007
Loading...

Share This Page