XSLT Transformation

Hello,

I'am trying to do an XSLT transformation from XML to HTML, but when I look at the HTML afterwards it just shows the XML code in the view source.  I have a string[] with multiple paths and this is how I'am transforming them:

   foreach (string webPath in webPaths)
                {
                    WebClient write = new WebClient();
                    Stream str = write.OpenRead(webPath);
                    TextReader tw = new StreamReader(str);
                    processServer(tw);

                    xslTrans.Load("stats_transform.xslt");
                    xslTrans.Transform(webPath, globalWriter);

                     tw.Close();
                }

And here are my globals:
public static XslCompiledTransform xslTrans = new XslCompiledTransform();
public static XmlTextWriter globalWriter = new XmlTextWriter("stats.html", null);

When I look at the HTML, I expected it to be formatted by my XSLT rules, but all I get is the data between the tags, and not even the tag names are being displayed.

This is a sample of my XML:
  <?xml version="1.0" encoding="us-ascii" standalone="yes" ?>
- <Host xmlns="myServer">
- <Drive xmlns="C:\">
  <Capacity>31.21</Capacity>
  <AmtUsed>23.06</AmtUsed>
  <AmtNotUsed>8.16</AmtNotUsed>
  <PercentFree>26</PercentFree>
  </Drive>
</Host>

My XSLT is like this (not fully functional - just for testing so far):
<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:msxsl="urn:schemas-microsoft-com:xslt" exclude-result-prefixes="msxsl">
    <xsl:output method="html" />

    <xsl:template match="/">
            <table border="1" cellspacing="1" align="center">
                  <xsl:for-each select="Host/Drive">
                        <tr>
                              <td>
                              Capacity: <xsl:value-of select="Capacity"/>
                              </td>
                        </tr>
                        
                  </xsl:for-each>
                  
            </table>
      </xsl:template>
</xsl:stylesheet>

Anyone have any ideas?
igor92128Asked:
Who is Participating?

[Product update] Infrastructure Analysis Tool is now available with Business Accounts.Learn More

x
I wear a lot of hats...

"The solutions and answers provided on Experts Exchange have been extremely helpful to me over the last few years. I wear a lot of hats - Developer, Database Administrator, Help Desk, etc., so I know a lot of things but not a lot about one thing. Experts Exchange gives me answers from people who do know a lot about one thing, in a easy to use platform." -Todd S.

zc2Commented:
your xml has two namespaces declarations:
xmlns="myServer" and  xmlns="C:\"
you need explicitly declate them in the xsl :
xmlns:m="myServer" xmlns:c="C:\"         (the names instead of "m" and "c"  may be any)
and them use the same names as the tag prefixes:

<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:msxsl="urn:schemas-microsoft-com:xslt" exclude-result-prefixes="msxsl"
    xmlns:m="myServer" xmlns:c="C:\">
    <xsl:output method="html" />
 
    <xsl:template match="/">
            <table border="1" cellspacing="1" align="center">
                  <xsl:for-each select="m:Host/c:Drive">
                        <tr>
                              <td>
                              Capacity: <xsl:value-of select="c:Capacity"/>
                              </td>
                        </tr>
                        
                  </xsl:for-each>
                  
            </table>
      </xsl:template>
</xsl:stylesheet>

Open in new window

igor92128Author Commented:
I just tried this and my HTML file is still just a bunch of numbers without tags or anything. So if I have xmlns in my XML file and they are different for each file, I'd need to build a pretty long XSLT file? I can't use for-each?

Maybe I'am not building my XML file correctly?

Iam declaring an xmlTextWriter: public static XmlTextWriter xwriter;

and using it like this:

xwriter = new XmlTextWriter(file, System.Text.Encoding.ASCII);
xwriter.WriteStartDocument(true);
xwriter.Formatting = Formatting.Indented;

xwriter.WriteStartElement("Host", gethostname());

foreach(DriveInfo d in alldrives)
{
xwriter.WriteStartElement("Drive", d.Name)
xwriter.WriteElementString("Capacity", d.Name, mycalculations);
...
...
xwriter.WriteEndElement();
}

            xwriter.WriteEndElement();
            xwriter.WriteEndDocument();
            xwriter.Close();
zc2Commented:
Did you intend to create the "Host" and "Drive" elements that way - with their value as a namespace?
It looks very odd...
(The second parameter  of WriteStartElement() creates a namespace declaration.)
Those values would be better stored in an named attribute using the WriteAttributeString() method.
Like:

xwriter.WriteStartElement("Host");
xwriter.WriteAttributeString("name", gethostname());
foreach(DriveInfo d in alldrives)
{
xwriter.WriteStartElement("Drive")
xwriter.WriteAttributeString("name", d.Name);
xwriter.WriteElementString("Capacity", d.Name, mycalculations);
...
...
xwriter.WriteEndElement();
}

Open in new window

Learn Ruby Fundamentals

This course will introduce you to Ruby, as well as teach you about classes, methods, variables, data structures, loops, enumerable methods, and finishing touches.

igor92128Author Commented:
This is my XML file now, but I would need to get rid of the xmlns statements right?

<?xml version="1.0" encoding="us-ascii" standalone="yes" ?>
- <Host Name="myhost">
- <Drive Name="C:\">
  <Capacity xmlns="C:\">74.45</Capacity>
  <AmtUsed xmlns="C:\">61.12</AmtUsed>
  <AmtNotUsed xmlns="C:\">13.33</AmtNotUsed>
  <PercentFree xmlns="C:\">18</PercentFree>
  </Drive>
  </Host>
igor92128Author Commented:
Ok, I got the XML correct now I think:

<Host Name="myhost">
- <Drive Name="C:\">
  <Size>74.45</Size>
  <AmtUsed>61.12</AmtUsed>
  <AmtNotUsed>13.33</AmtNotUsed>
  <PercentFree>18</PercentFree>
  </Drive>
  </Host>

Will try to do the XSLT transform with this.
zc2Commented:
your last xml does not contain the Capacity element...
igor92128Author Commented:
I just renamed Capacity. Ok, I got it working but I have 1 more problem:

How do I select the value inside the tags for Host and Drive? Those values are blank in the result HTML file. All other values show up fine. Sample XSLT code is below.
<body>
				<p>
					Host: <xsl:for-each select="/Host"><br/>
						Drive: <xsl:for-each select="/Host/Drive"><br/>
							Capacity: <xsl:value-of select="Size"/><br/>
							Amount Used: <xsl:value-of select="AmtUsed"/><br/>

Open in new window

zc2Commented:
add a "@" before the attribute name to address its value, like:
Drive: <xsl:value-of select="@Name"/><br/>

The latest xslt is not quite correct.
You have two for-each loops: one for hosts and one for drives in each host.

But in your solution the inner loop will enumerate _all_ drives from all hosts.
The following enumerqates drives only in the current host:
<body>
  <p>
    <xsl:for-each select="Host">
      Host: <xsl:value-of select="@Name"/><br/>
       <xsl:for-each select="Drive">
         Drive: <xsl:value-of select="@Name"/><br/>
         Capacity: <xsl:value-of select="Size"/><br/>
         Amount Used: <xsl:value-of select="AmtUsed"/><br/>
       </xsl:for-each>
    </xsl:for-each>
  </p>
</body>

Open in new window

Experts Exchange Solution brought to you by

Your issues matter to us.

Facing a tech roadblock? Get the help and guidance you need from experienced professionals who care. Ask your question anytime, anywhere, with no hassle.

Start your 7-day free trial
It's more than this solution.Get answers and train to solve all your tech problems - anytime, anywhere.Try it for free Edge Out The Competitionfor your dream job with proven skills and certifications.Get started today Stand Outas the employee with proven skills.Start learning today for free Move Your Career Forwardwith certification training in the latest technologies.Start your trial today
.NET Programming

From novice to tech pro — start learning today.