从许多xml文件中提取特定信息

时间:2014-01-03 11:13:39

标签: xml search powershell

我有一个脚本,它导出我们的用户软件并运行注册表项到xml文件,以便我们跟踪可疑文件。我有几百个xml文件,包括:

<MDetection>
   <SoftwareReg>
      <Soft1>HKCU\SOFTWARE\Adobe</Soft1>
      <Soft2>HKCU\SOFTWARE\Ask.com</Soft2>
      <Soft3>HKCU\SOFTWARE\Citrix</Soft3>
      <Soft4>HKCU\SOFTWARE\Google</Soft4>
      ...
   </SoftwareReg>
   <RunReg>
      <Run1>SOFTWARE\Microsoft\Windows\Currentversion\Run\Sidebar-->C:\Program Files\Windows Sidebar\sidebar.exe /autoRun</Run1> 
      <Run2>SOFTWARE\Microsoft\Windows\Currentversion\Run\WindowsWelcomeCenter-->rundll32.exe oobefldr.dll,ShowWelcomeCenter</Run2> 
      ...
   </RunReg>
   <Hostname>USERPC01</Hostname>
   <Username>JonesA</Username>
   <TimeGenerated>03/01/14 11:00</TimeGenerated>
</MDetection>

我希望能够搜索特定SoftwareReg或RunReg密钥的所有XML文件,并且还能够使用通配符搜索条目。例如,搜索所有'Ask.com'键或以'cr'开头的条目。

我遇到的问题是我想知道相应的reg键所引用的主机名和用户名。我无法提取这些。

我的Xml Powershell并不是最强大的,所以任何帮助都会受到赞赏!我目前正在使用:

   $XmlData = Select-Xml -Path '\\Server\Share$\*.xml' -XPath '//MDetection' -ErrorAction 'silentlycontinue'
   $XmlData | %{$a += $_.Node.SoftwareReg.ChildNodes.'#text'}

我使用$ a临时存储所有reg条目,但我无法提取主机名或用户名。我怀疑有一种更简单的方法,我目前正在使用它!

非常感谢,

3 个答案:

答案 0 :(得分:1)

尝试select将信息转换为自定义对象:

$XmlData | select @{
    n='Software';e={$_.Node.SoftwareReg.ChildNodes.'#text' | ? {$_ -ne $null}}
  },
  @{n='Hostname';e={$_.Node.Hostname.ToString()}},
  @{n='Username';e={$_.Node.Username.ToString()}}

上面创建了属性Software包含具有注册表路径的数组的对象。要将分层数据转换为表格数据,您可以尝试这样的事情:

$XmlData | % {
  $username = $_.Node.Username.ToString()
  $hostname = $_.Node.Hostname.ToString()

  $_.Node.SoftwareReg.ChildNodes.'#text' | ? { $_ -ne $null } |
    select @{n='Software';e={$_}},
      @{n='Hostname';e={$hostname}},
      @{n='Username';e={$username}}
}

答案 1 :(得分:0)

我不得不做类似的事情。

这样做的方法利用了XSLT,你可以在这里了解http://www.w3schools.com/xsl/default.asp 教程应该足以满足您的需求。这种语言可以做很复杂的事情。

答案 2 :(得分:0)

认识到使用正则表达式来解析XML可能被认为是异端邪说:

$search = 'Ask.com'
$Rsearch = [regex]::Escape($search)

$regex=@"
(?ms)<MDetection>
   <SoftwareReg>.+?$Rsearch.+?
   </RunReg>
   <Hostname>(.+?)</Hostname>
   <Username>(.+?)</Username>
   .+
"@


(Get-Content file.xml -Raw) -match $regex > $nul
$matches


Name                           Value                                                                 
----                           -----                                                                 
2                              JonesA                                                                
1                              USERPC01                                                              
0                              <MDetection>...