In the last post, we worked with CSV types of files. The next type of file we're going to look at is Extensible markup language(XML). They are used for various reasons, for example, storing properties data that can be used for configuration and data storage.
XML is one of the basic file extensions and consists of opening and closing tags..
<config>
<pctype>
<type name="Desktop PC" value="D"></type>
<type name="Notebook" value="N"></type>
<type name="Tablet PC" value="T"></type>
</pctype>
<logdir>E:Logs</logdir>
<logfile>SCCMLogs.txt</logfile>
</config>
Parameters can be added both in a nested fashion and inline. By using the nested approach, you will also have a visual recognition of which objects are on the same level through indentation:
We will start with an example of storing and loading configuration data💗
PS C:\WINDOWS\system32> $XMlcontent= @'
<config>
<pctype>
<type name="Desktop PC" value="D"></type>
<type name="Notebook" value="N"></type>
<type name="Tablet PC" value="T"></type>
</pctype>
<logdir>E:Logs</logdir>
<logfile>SCCMLogs.txt</logfile>
</config>
'@
Now let's try to save the file and then read the content of the XML file as an XML object. To do this we perform the following steps.
PS C:\WINDOWS\system32> #Path where the config file is being saved
$configPath = 'c:\users\config.xml'
#Saving config file
$XMlcontent | Set-Content $configPath
#Loading xml as config
[XML] $configXml = Get-Content -Path $configPath -ErrorAction 'Stop'
Now let's check what we have got in that XML object i.e $configXml
PS C:\WINDOWS\system32> $configXml
xml config
--- ------
version="1.0" standalone="yes" config
We saw how the XML file can be loaded easily with PowerShell and using the configuration data. The implementation is very straightforward and involves casting the loaded content with [XML] into an XML file. This allows us to directly work with IntelliSense and find our configuration properties easily.
We have the object we can now try various tasks like parsing the XML,reading the top nodes, Filtering or searching tags/values. Let's understand with an example.
Let's try to fetch all the PCType values.
PS C:\WINDOWS\system32> $configXml.config.PCType.Type
Name Value
---- -----
Desktop PC D
Notebook N
Tablet PC T
I also learned about the grid view which outputs the results in a screen in tabular format.
PS C:\WINDOWS\system32> $configXml.config.PCType.Type | Out-GridView
Filtering the only type of notebook can be done by applying the where-object. we will see in the below example how we can achieve the same.
PS C:\WINDOWS\system32> $NotebookCode = ($configXml.Config.PCType.Type | Where-Object {$_.Name -like 'Notebook'}).Value
PS C:\WINDOWS\system32> $NotebookCode
N
Also, we can run some condition along within the object to see if some value exists
PS C:\WINDOWS\system32> if ($configXml.Config.Logdir -ne $null)
{
$LogDir = $configXml.Config.Logdir
$LogFile = $configXml.Config.LogFile
}
PS C:\WINDOWS\system32> $LogDir
E:\Logs\
PS C:\WINDOWS\system32> $LogFile
SCCMLogs.txt
It is possible to use filtering and searching to find configuration properties. Especially when you are working with very complex configuration files, this technique might come in handy.
In the next example🙏, we will take a more programmatic approach to find the values of an XML file by using XPath filters.
XPath filters allow us to find and retrieve objects in bigger, more complex XML files.
[xml]$xml = Get-Content 'C:\path\to\your.xml'
$xml.selectNodes('//person') | select Name
Just as regular expressions are the standard way to interact with plain text, XPath is the standard way to interact with XML. Because of that, XPath is something you are likely to run across in your travels. Several cmdlets support XPath queries: Select-Xml, Get-WinEvent, and more.
Here we have an example of working with Xpath
PS C:\WINDOWS\system32> $Xpath = "/config/PCType"
PS C:\WINDOWS\system32> Select-Xml -Path $Path -XPath $Xpath | Select-Object -ExcludeProperty Node
Node Path Pattern
---- ---- -------
PCType C:\temp\config.xml /config/PCType
To make use of XPath filters, you can work with the Select-Xml cmdlet and add the XPath filter as a string. We used a simple filter here to retrieve the objects for a specific structure with "/Types/Type" , and to retrieve all values for all included types recursively with "//config".
Conclusion:
In the past, XML has been widely used as an option for storing application data. XML has some limitations though. It begins to struggle as your XML files increase in size (>1 MB), or if many people try to work with them simultaneously. But it still remains powerful when we are working with configuration or dynamic properties handling.
Happy Coding 👍
EmoticonEmoticon