无法在 PowerShell 中完全解析 XML [英] Unable to completely parse XML in PowerShell

查看:38
本文介绍了无法在 PowerShell 中完全解析 XML的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个 XML 文件,我想通过它解析并检索特定信息.

为了便于理解,以下是 XML 文件外观的屏幕截图:

我想解析 XML 并为每个 Item 节点检索屏幕截图中指示的字段.检索到的每个值都需要按项目节点进行格式化.

最后,我希望能够指定要查找的条件,并且只在找到的位置检索该条件.

我一直在尝试,但没有运气.这是我能够想出的:

[xml]$MyXMLFile = gc 'X:\folder\my.xml'$XMLItem = $MyXMLFile.PatchScan.Machine.Product.Item$Patch = $XMLItem |Where-Object {$_.Class -eq 'Patch'}$Patch.BulletinID$Patch.PatchName$Patch.Status

当我运行上面的代码时,它没有返回任何结果.但是,仅出于测试目的,我删除了 Item 部分.现在,我可以通过修改上面的代码来让它工作.

我将 XML 加载到 XML 对象中.现在我尝试将其遍历到产品,并且效果很好:

<前>PS> $xmlobj.PatchScan.Machine.Product |选择对象 - 属性名称,SP名称 SP---- -Windows 10 专业版 (x64) 1607Internet Explorer 11 (x64) 黄金版Windows Media Player 12.0 黄金版MDAC 6.3 (x64) 金.NET Framework 4.7 (x64) 黄金版MSXML 3.0 SP11MSXML 6.0 (x64) SP3DirectX 9.0c 黄金版Adobe Flash 23 金VMware Tools x64 金牌Microsoft Visual C++ 2008 SP1 Redistributable GoldMicrosoft Visual C++ 2008 SP1 Redistributable (x64) Gold

现在添加 Item ,Intellisense 会加一个括号,好像 Item 是一个方法 $xmlobj.PatchScan.Machine.Product.Item( ← 看到了吗?所以这就是为什么我认为有些Item 节点做一些奇怪的事情的原因,这是我的障碍.

此屏幕截图更好地显示了它如何从多个产品文件夹开始,然后在每个产品文件夹中包含多个项目文件夹.

产品文件夹中的 XML 我不关心.我需要每个项目文件夹中的个人信息.

解决方案

XML 是一种结构化文本格式.它对文件夹"一无所知.您在屏幕截图中看到的只是用于显示数据的程序如何呈现数据.

无论如何,获得所需内容的最佳方法是使用 SelectNodes()XPath 表达式.像往常一样.

[xml]$xml = Get-Content 'X:\folder\my.xml'$xml.SelectNodes('//Product/Item[@Class="Patch"]') |选择对象公告 ID、补丁名称、状态

I have an XML file that I would like to parse through, and retrieve back specific information.

To make it easy to understand, here is a screenshot of what the XML file looks like:

I would like to parse through the XML and for each Item node, retrieve back the fields indicated in the screenshot. Each of the values retrieved need to be formatted per item node.

Finally, I would love to be able to specify a criteria to look for, and only retrieve that where found.

I have been trying, without luck. Here is what I have been able to come up with:

[xml]$MyXMLFile = gc 'X:\folder\my.xml'
$XMLItem = $MyXMLFile.PatchScan.Machine.Product.Item
$Patch = $XMLItem | Where-Object {$_.Class -eq 'Patch'}
$Patch.BulletinID
$Patch.PatchName
$Patch.Status

When I run the above code, it returns no results. However, for testing purposes only, I remove the Item portion. Now, I can get it working by modifying the code above.

I load the XML into an XML Object. Now I try traverse it down to product and it works perfectly:

PS> $xmlobj.PatchScan.Machine.Product | Select-Object -Property Name, SP

Name SP
---- --
Windows 10 Pro (x64) 1607
Internet Explorer 11 (x64) Gold
Windows Media Player 12.0 Gold
MDAC 6.3 (x64) Gold
.NET Framework 4.7 (x64) Gold
MSXML 3.0 SP11
MSXML 6.0 (x64) SP3
DirectX 9.0c Gold
Adobe Flash 23 Gold
VMware Tools x64 Gold
Microsoft Visual C++ 2008 SP1 Redistributable Gold
Microsoft Visual C++ 2008 SP1 Redistributable (x64) Gold

Now add Item in and Intellisense puts up a bracket as if Item was a method $xmlobj.PatchScan.Machine.Product.Item( ← See that? So that is why I think for some reason the Item node is doing something strange and that is my roadblock.

This screenshot shows better how it starts with many product folders, and then in each product folder is many item folders.

The XML in the product folder I don't care about. I need the individual information in each item folder.

解决方案

XML is a structured text format. It knows nothing about "folders". What you see in your screenshots is just how the the data is rendered by program you use for displaying it.

Anyway, the best approach to get what you want is using SelectNodes() with an XPath expression. As usual.

[xml]$xml = Get-Content 'X:\folder\my.xml'
$xml.SelectNodes('//Product/Item[@Class="Patch"]') |
    Select-Object BulletinID, PatchName, Status

这篇关于无法在 PowerShell 中完全解析 XML的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆