1

I'm having trouble getting a properly formatted XML file using the following code:

# Get Computer System info
$CompInfo = Get-WmiObject Win32_ComputerSystem
$CompName = $CompInfo.Name

# Get IP Address
$IPAddressTemp = Test-Connection $CompName -count 1 | select Address,Ipv4Address
$IPAddress = $IPAddressTemp.IPV4Address

# Begin Writing values to XML Document
$filePath = "C:\Temp\$CompName.$IPAddress.xml" # Set the File Name
$XmlWriter = New-Object System.XMl.XmlTextWriter($filePath,$Null) # Create The Document
# Set The XML Formatting
$xmlWriter.Formatting = "Indented"
$xmlWriter.Indentation = "4"

# Start the XML Document
$xmlWriter.WriteStartDocument()

# Set the XSL
$XSLPropText = "type='text/xsl' href='style.xsl'"
$xmlWriter.WriteProcessingInstruction("xml-stylesheet", $XSLPropText)

$xmlWriter.WriteStartElement("Server") # Write Root Element

# Write the Basic System Elements to the XML Document
$xmlWriter.WriteStartElement("SystemInfo")
$xmlWriter.WriteElementString("Hostname","$CompName")
$xmlWriter.WriteElementString("IPAddress","$IPAddress")
$xmlWriter.WriteStartElement("Drives") # Add drive information as individual elements

# Get drive information and add each to XML
$logicalDisk = Get-WmiObject Win32_LogicalDisk -Filter "DriveType=3" ComputerName localhost
$count=0
foreach($disk in $logicalDisk)
{
$diskObj = "" | Select-Object Disk,Size,FreeSpace
$diskObj.Disk = $disk.DeviceID
$diskObj.Size = "{0:n0} GB" -f (($disk | Measure-Object -Property Size -Sum).sum/1gb)
$diskObj.FreeSpace = "{0:n0} GB" -f (($disk | Measure-Object -Property FreeSpace -Sum).sum/1gb)
$DriveLetter = $diskObj.Disk
$DriveSize = $diskObj.Size
$DriveFreeSpace = $diskObj.FreeSpace
$xmlWriter.WriteStartElement("Disk$count") # Add tag for each drive
$xmlWriter.WriteElementString("DriveLetter","$DriveLetter") # Write Drive Letter to XML
$xmlWriter.WriteElementString("DriveSize","$DriveSize") # Write Drive Size to XML
$xmlWriter.WriteElementString("DriveFreeSpace","$DriveFreeSpace") # Write Drive Free Space to XML
$xmlWriter.WriteEndElement # <-- Closing Drive Tag
$count++
}
# Write Close Tag for Drives and SysInfo elements
$xmlWriter.WriteEndElement # <-- Closing Drives Tag
$xmlWriter.WriteEndElement # <-- Closing SystemInfo
# Write Close Tag for Root Element
$xmlWriter.WriteEndElement # <-- Closing Server

# End the XML Document
$xmlWriter.WriteEndDocument()

# Finish The Document
$xmlWriter.Finalize
$xmlWriter.Flush
$xmlWriter.Close()

The XML output looks like this:

<?xml version="1.0"?>
<?xml-stylesheet type='text/xsl' href='style.xsl'?>
<Server>
        <SystemInfo>
            <Hostname>TEST-SERVER</Hostname>
            <IPAddress>10.0.0.10</IPAddress>
            <Drives>
                <Disk0>
                <DriveLetter>C:</DriveLetter>
                <DriveSize>223 GB</DriveSize>
                <DriveFreeSpace>34 GB</DriveFreeSpace>
                <Disk1>
                    <DriveLetter>D:</DriveLetter>
                    <DriveSize>931 GB</DriveSize>
                    <DriveFreeSpace>547 GB</DriveFreeSpace>
                    <Disk2>
                        <DriveLetter>E:</DriveLetter>
                        <DriveSize>466 GB</DriveSize>
                        <DriveFreeSpace>466 GB</DriveFreeSpace>
                        <Disk3>
                            <DriveLetter>G:</DriveLetter>
                            <DriveSize>931 GB</DriveSize>
                            <DriveFreeSpace>159 GB</DriveFreeSpace>
                        </Disk3>
                    </Disk2>
                </Disk1>
            </Disk0>
        </Drives>
    </SystemInfo>
</Server>

And this is how I need to have it appear:

<?xml version="1.0"?>
<?xml-stylesheet type='text/xsl' href='style.xsl'?>
<Server>
    <SystemInfo>
        <Hostname>TEST-SERVER</Hostname>
        <IPAddress>10.0.0.10</IPAddress>
        <Drives>
            <Disk0>
                <DriveLetter>C:</DriveLetter>
                <DriveSize>223 GB</DriveSize>
                <DriveFreeSpace>34 GB</DriveFreeSpace>
            </Disk0>
            <Disk1>
                <DriveLetter>D:</DriveLetter>
                <DriveSize>931 GB</DriveSize>
                <DriveFreeSpace>547 GB</DriveFreeSpace>
            </Disk1>
            <Disk2>
                <DriveLetter>E:</DriveLetter>
                <DriveSize>466 GB</DriveSize>
                <DriveFreeSpace>466 GB</DriveFreeSpace>
            </Disk2>
            <Disk3>
                <DriveLetter>G:</DriveLetter>
                <DriveSize>931 GB</DriveSize>
                <DriveFreeSpace>159 GB</DriveFreeSpace>
            </Disk3>
        </Drives>
    </SystemInfo>
</Server>

Can someone tell me what I'm doing wrong?

Thanks

1 Answer 1

2

You're missing a set of parentheses (()) at the end of $XmlWriter.WriteEndElement:

$xmlWriter.WriteStartElement("Disk$count") # Add tag for each drive
$xmlWriter.WriteElementString("DriveLetter","$DriveLetter") # Write Drive Letter to XML
$xmlWriter.WriteElementString("DriveSize","$DriveSize") # Write Drive Size to XML
$xmlWriter.WriteElementString("DriveFreeSpace","$DriveFreeSpace") # Write Drive Free Space to XML
$xmlWriter.WriteEndElement() # <-- Closing Drive Tag - don't forget the the ()

Without the (), it just returns a PSMethod object with the method's signature(s), but it's never executed, which is why your <Drives> child elements keep nesting

Sign up to request clarification or add additional context in comments.

2 Comments

Thanks Mathias. I've been staring at the code for 2 hours and missed something so simple!
@W.J.P. Glad to help. Don't beat yourself up, it used to happen to me all the time ;-)

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.