从 .xml 文件中提取节点数据时,.csv 文件为空

问题描述 投票:0回答:1

再试一次。好的,我有一个 powershell 脚本来处理目录中的 .xml 文件。对于每个 .xml 文件,脚本都会处理它,查找每个实例并提取每个节点内的所有数据。

当我尝试将结果写入 .csv 文件时,我遇到的挑战是空的。没有标题,没有数据,什么都没有。我一直在绞尽脑汁为什么它不简单地将数据写入 .csv 文件

代码

# Define the directory containing the XML files
$directory = "C:\test\"

# Get all XML files in the directory
$xmlFiles = Get-ChildItem -Path $directory -Filter *.xml

# Loop through each XML file
foreach ($file in $xmlFiles) {
    # Load the XML content
    [xml]$xmlContent = Get-Content -Path $file.FullName

    # Initialize an array to hold the extracted data
    $data = @()

    # Loop through each AuditRecord node
    foreach ($auditRecord in $xmlContent.SelectNodes("//AuditRecord")) {
        $record = New-Object PSObject -Property @{
        AuditRecordID = AuditRecordID
        UserID = PIUser.UserID
        UserName = PIUser.Name
        UTCSeconds = PITime.UTCSeconds
        LocalDate = PITime.LocalDate
        PIModuleAction = PIConfigurationDB.PIModules.Action
        PIModuleUniqueID = PIConfigurationDB.PIModules.PIModule.UniqueID -join ", "
        PIModuleName = PIConfigurationDB.PIModules.PIModule.Name
        PIModuleAttribName = PIConfigurationDB.PIModules.PIModule.PIModuleAttributes.PIModuleAttribute.Name -join ", "
        DateTimeXSBefore = PIConfigurationDB.PIModules.PIModule.PIModuleAttributes.PIModuleAttribute.Value.Before.Type[0]
        DateTimeXSAfter = PIConfigurationDB.PIModules.PIModule.PIModuleAttributes.PIModuleAttribute.Value.After.Type[0]
        PIModuleAttribName2 = PIConfigurationDB.PIModules.PIModule.PIModuleAttributes.PIModuleAttribute.Name[1]
        LongBefore = PIConfigurationDB.PIModules.PIModule.PIModuleAttributes.PIModuleAttribute.Value.Before.Type[1]
        LongAfter = PIConfigurationDB.PIModules.PIModule.PIModuleAttributes.PIModuleAttribute.Value.After.Type[1]
        PIModuleAttribName3 = PIConfigurationDB.PIModules.PIModule.PIProperties.PIProperty.Name
        PIPropertyName = PIConfigurationDB.PIModules.PIModule.PIProperties.PIProperty.Action
        PIPropertyAction = PIConfigurationDB.PIModules.PIModule.PIProperties.PIProperty.ParentUNC_Name
        hexbinBefore = PIConfigurationDB.PIModules.PIModule.PIProperties.PIProperty.Value.Before.Type
        hexbinAfter = PIConfigurationDB.PIModules.PIModule.PIProperties.PIProperty.Value.After.Type
        }
        $data += $record
    }

    # Define the output CSV file path
    $csvFilePath = Join-Path -Path $directory -ChildPath ($file.BaseName + ".csv")

    # Export the data to a CSV file
    $data | Export-Csv -Path $csvFilePath -NoTypeInformation
}

.XML 示例

<AuditRecord AuditRecordID="b066447a-20de-4659-8e5e-41ecb27d9d39">
<PIUser UserID="1" Name="piadmin"/>
<PITime UTCSeconds="1711662501" LocalDate="2024-03-28T17:48:21-04:00" />
<PIConfigurationDB>
<PIModules Action="Edit">
<PIModule UniqueID="feea9e80-3d3f-4f45-b58d-275e4845bcde, 31-Dec-69 16:00:01" Name="Database">
<PIModuleAttributes>
<PIModuleAttribute Name="ModifyDate">
<Value>
<Before Type="xs:dateTime">2024-03-28T17:47:42-04:00</Before>
<After Type="xs:dateTime">2024-03-28T17:48:21-04:00</After>
</Value>
</PIModuleAttribute>
<PIModuleAttribute Name="Revision">
<Value>
<Before Type="xs:long">35738</Before>
<After Type="xs:long">35739</After>
</Value>
</PIModuleAttribute>
</PIModuleAttributes>
<PIProperties>
<PIProperty Name="TemplateDataSet" Action="Edit" ParentUNC_Name="\\PIProperties">
<Value>
<Before Type="xs:hexBinary"></Before>
<After Type="xs:hexBinary"></After>
</Value>
</PIProperty>
</PIProperties>
</PIModule>
</PIModules>
</PIConfigurationDB>
</AuditRecord>

期望的输出

enter image description here

excel xml powershell parsing tags
1个回答
0
投票
$Directory = 'C:\Test\'

Get-ChildItem -Path $Directory -Filter *.xml | %{
    $CsvFilePath = Join-Path -Path $Directory -ChildPath ($_.BaseName + ".csv")
    [xml](Get-Content -Path $_.FullName) |
        Select-Xml "//AuditRecord" | 
        Select-Object -ExpandProperty Node | %{
            [PSCustomObject]@{
                AuditRecordID = $_.AuditRecordID
                UserID = $_.PIUser.UserID
                UserName = $_.PIUser.Name
                UTCSeconds = $_.PITime.UTCSeconds
                LocalDate = $_.PITime.LocalDate
                PIModuleAction = $_.PIConfigurationDB.PIModules.Action
                PIModuleUniqueID = $_.PIConfigurationDB.PIModules.PIModule.UniqueID -join ", "
                PIModuleName = $_.PIConfigurationDB.PIModules.PIModule.Name
                PIModuleAttribName = $_.PIConfigurationDB.PIModules.PIModule.PIModuleAttributes.PIModuleAttribute.Name -join ", "
                DateTimeXSBefore = $_.PIConfigurationDB.PIModules.PIModule.PIModuleAttributes.PIModuleAttribute.Value.Before.Type[0]
                DateTimeXSAfter = $_.PIConfigurationDB.PIModules.PIModule.PIModuleAttributes.PIModuleAttribute.Value.After.Type[0]
                PIModuleAttribName2 = $_.PIConfigurationDB.PIModules.PIModule.PIModuleAttributes.PIModuleAttribute.Name[1]
                LongBefore = $_.PIConfigurationDB.PIModules.PIModule.PIModuleAttributes.PIModuleAttribute.Value.Before.Type[1]
                LongAfter = $_.PIConfigurationDB.PIModules.PIModule.PIModuleAttributes.PIModuleAttribute.Value.After.Type[1]
                PIModuleAttribName3 = $_.PIConfigurationDB.PIModules.PIModule.PIProperties.PIProperty.Name
                PIPropertyName = $_.PIConfigurationDB.PIModules.PIModule.PIProperties.PIProperty.Action
                PIPropertyAction = $_.PIConfigurationDB.PIModules.PIModule.PIProperties.PIProperty.ParentUNC_Name
                hexbinBefore = $_.PIConfigurationDB.PIModules.PIModule.PIProperties.PIProperty.Value.Before.Type
                hexbinAfter = $_.PIConfigurationDB.PIModules.PIModule.PIProperties.PIProperty.Value.After.Type       
            }
        } | Export-Csv -Path $CsvFilePath -NoTypeInformation
}

将会导致

"AuditRecordID","UserID","UserName","UTCSeconds","LocalDate","PIModuleAction","PIModuleUniqueID","PIModuleName","PIModuleAttribName","DateTimeXSBefore","DateTimeXSAfter","PIModuleAttribName2","LongBefore","LongAfter","PIModuleAttribName3","PIPropertyName","PIPropertyAction","hexbinBefore","hexbinAfter"
"b066447a-20de-4659-8e5e-41ecb27d9d39","1","piadmin","1711662501","2024-03-28T17:48:21-04:00","Edit","feea9e80-3d3f-4f45-b58d-275e4845bcde, 31-Dec-69 16:00:01","Database","ModifyDate, Revision","xs:dateTime","xs:dateTime","Revision","xs:long","xs:long","TemplateDataSet","Edit","\\PIProperties","xs:hexBinary","xs:hexBinary"

那么我们来谈谈吧 首先,您的一些 XML 路径略有错误 示例

$_.PIConfigurationDB.PIModules.PIModule.PIModuleAttributes.PIModuleAttribute.Value.Before.Type[0]

退货

xs:dateTime

你想要的更像是

$_.PIConfigurationDB.PIModules.PIModule.PIModuleAttributes.PIModuleAttribute.Value.Before[0].'#text'

退货

2024-03-28T17:47:42-04:00

似乎有一些类似的情况,只需要稍微调整一下路径。

那么为什么你的脚本不起作用?

让我们看一下代码示例

foreach ($auditRecord in $xmlContent.SelectNodes("//AuditRecord")) {
    $record = New-Object PSObject -Property @{
        AuditRecordID = AuditRecordID
        UserID = PIUser.UserID
    }
}

我希望你的代码会出现上面的错误

您正在使用 var $auditRecord 循环 XML //AuditRecord

但是当您进入循环时,在设置 PSObject 属性的值时不会调用 $auditRecord

我希望看到的更像是

foreach ($auditRecord in $xmlContent.SelectNodes("//AuditRecord")) {
    $record = New-Object PSObject -Property @{
        AuditRecordID = $auditRecord.AuditRecordID
        UserID = $auditRecord.PIUser.UserID
    }
}
© www.soinside.com 2019 - 2024. All rights reserved.