xml - 对 XML 子节点进行过滤

标签 xml powershell msbuild

我正在尝试处理 MSBuild 文件,以使用下面的 PowerShell 代码段提取 Include 属性中的文件名。

Get-ChildItem $xmlFile |
    ForEach-Object { Write-Host $_.FullName; [xml](Get-Content $_) } |
    Where-Object {
        (($_.Project.ItemGroup -ne $null) -and
        ($_.Project.ItemGroup.ProjectFile -ne $null))
    } -ErrorAction SilentlyContinue |
    ForEach-Object { $_.Project.ItemGroup.ProjectFile } |
    Where-Object { ($_.Include -ne $null) } |
    ForEach-Object { Write-Host $_ }

这对于具有 ItemGroup 子元素的 XML 来说效果很好,如下所示:

<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
  <Import Project="settings.props" />
  <ItemGroup>
    <ProjectFile Include="filename.proj"/>

但是,当 XML 层次结构不同(没有 ItemGroup 元素)时(如下所示),脚本会失败并出现错误:

The property 'ItemGroup' cannot be found on this object. Verify that the property exists.

即使是 ErrorAction 也不会抑制错误输出。

如何在管道中检查子元素是否存在并跳过不存在的文件?另外,为什么 -ErrorAction 参数不起作用?

最佳答案

您不需要使用 Get-Content加载该文件,将其转换xml并尝试自己选择节点。只需使用 Select-XML cmdlet:

Get-ChildItem $xmlFile | ForEach-Object {
    $node = Select-Xml -Path $_.FullName `
        -XPath '/n:Project/n:ItemGroup/n:ProjectFile/@Include' `
        -Namespace @{n = 'http://schemas.microsoft.com/developer/msbuild/2003'}

    if ($node)
    {
        $node.Node.Value
    }
}

它使用xpath来选择Include属性(和命名空间)。

输出:

filename.proj

关于xml - 对 XML 子节点进行过滤,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/37691781/

相关文章:

powershell - 使用映射到表(例如 csv)覆盖平面文件

javascript - 获取 0 作为状态

C#- XML 文档在其他项目中不可用

xml - 使用XML和R有效地获取具有特定名称的子代数

PowerShell:Start-Job 中的 $input 到底是什么?

azure - 如何使用 powershell 重新启动容器实例

c# - 自定义 MSBuild 任务 : how to flush logging in VS2012 output window while task is still running?

MSBuild 更新 csproj 中的属性

ios - Xamarin MSBuild - 错误 MSB3323 : Unable to find manifest signing certificate in the certificate store

xml - ORA-01861 : literal does not match format string when parsing XML date