powershell - EventLogPropertySelector 未从 PowerShell 中的事件对象返回扩展数据

标签 powershell xpath get-winevent

我的短期目标是与提供商 Microsoft-Windows-TerminalServices-LocalSessionManager 收集事件 ID 40 和 42来自名为 Microsoft-Windows-TerminalServices-**LocalSessionManager/Operational 的日志然后根据 Session/SessionID 对它们进行排序。虽然我可以尝试解析消息属性,但我正在尝试使用 EventLogRecordGetPropertyValues 方法,该方法采用 System.Diagnostics.Eventing.Reader.EventLogPropertySelector 范围。此外,对于事件 40 的消息, session ID 首先显示为标记为“Session”的 session ID,对于事件 41 的消息,则显示第二个标记为“SessionID”的 session ID。

<表类=“s-表”> <标题> 名称 成员类型 定义 <正文> 获取属性值 方法 System.Collections.Generic.IList[System.Object]

我在 2018 年就看到了 Peter-CoreMathias R. Jessen两者都给出了如何做到这一点的答案。按照他们的示例,我查看了事件提供者的事件模板。

(Get-WinEvent -ListProvider Microsoft-Windows-TerminalServices-LocalSessionManager).Events|Where-object{@(40,42) -contains $_.ID}

Id          : 40
Version     : 0
LogLink     : System.Diagnostics.Eventing.Reader.EventLogLink
Level       : System.Diagnostics.Eventing.Reader.EventLevel
Opcode      : System.Diagnostics.Eventing.Reader.EventOpcode
Task        : System.Diagnostics.Eventing.Reader.EventTask
Keywords    : {}
Template    : <template xmlns="http://schemas.microsoft.com/win/2004/08/events">
<data name="Session" inType="win:UInt32" outType="xs:unsignedInt"/>
<data name="Reason" inType="win:UInt32" outType="xs:unsignedInt"/>
</template>

Description : Session %1 has been disconnected, reason code %2

Id          : 42
Version     : 0
LogLink     : System.Diagnostics.Eventing.Reader.EventLogLink
Level       : System.Diagnostics.Eventing.Reader.EventLevel
Opcode      : System.Diagnostics.Eventing.Reader.EventOpcode
Task        : System.Diagnostics.Eventing.Reader.EventTask
Keywords    : {}
Template    : <template xmlns="http://schemas.microsoft.com/win/2004/08/events">
                <data name="User" inType="win:UnicodeString" outType="xs:string"/>
                <data name="SessionID" inType="win:UInt32" outType="xs:unsignedInt"/>
              </template>

Description : End session arbitration:

              User: %1
              Session ID: %2

作为测试,我创建了以下代码来尝试从事件 ID 42 获取 session ID:

$strComputerName='PMV-SC01'
<# For those wanting to build xmlFilters try something like the following as it allow you to create them more dynamically
$xmlFilterBase=[xml]'<QueryList><Query Id="0"></Query></QueryList>'
## in a loop ##
$xmlSelect=$xmlFilter.CreateElement("Select")
$xmlSelect.SetAttribute("Path","$Logname")
$xmlSelect.set_InnerText("*[System[$($ProviderName)TimeCreated[@SystemTime>='$StartTime' and @SystemTime<='$EndTime']]]")
$xmlFilter.QueryList.Query.AppendChild($xmlSelect)|Out-Null
$xmlSelect=$Null
## end loop ##
#>
#I used the filter below to simplify the testing.
$xmlFilter=@"
<QueryList><Query Id="0" Path="Microsoft-Windows-TerminalServices-LocalSessionManager/Operational"><Select Path="Microsoft-Windows-TerminalServices-LocalSessionManager/Operational">*[System[TimeCreated[@SystemTime&gt;='2021-06-28T22:00:00.000Z' and @SystemTime&lt;='2021-06-28T23:00:00.000Z']]]</Select></Query></QueryList>
"@
$WinEvents=Get-WinEvent -ComputerName $strComputerName -FilterXml $xmlFilter -Oldest|Where-object{$_.Id -eq 42}
$WinEvents.count
# output is 10
$SelectorStrings= [String[]]@(
'Event/EventData/Data[@name="SessionID"]'
)
$PropertySelector= [System.Diagnostics.Eventing.Reader.EventLogPropertySelector]::new($SelectorStrings)
$WinEvents|ForEach-Object{$TheSessionIds=@();$TheSessionIds+=$_.GetPropertyValues($PropertySelector)}
$TheSessionIds.count
#output is 1
# All of the follow also return nothing:
$WinEvents[1].GetPropertyValues($PropertySelector)
$WinEvents.GetPropertyValues($PropertySelector)
$1WinEvent=$WinEvents[0]
$1WinEvent.GetPropertyValues($PropertySelector)

没有错误消息。 GetPropertyValues() 方法不返回任何内容。 PowerShell版本:5.1.14393.2457

<表类=“s-表”> <标题> Windows 版本 版本 操作系统构建 <正文> Windows 服务器 2016 标准 1607 14393.2457

( Get-WindowsVersion credit )

我的长期目标是生成类似以下输出的内容。这篇文章的请求是帮助从 GetPropertyValues 方法获取值。我也想在其他项目中使用这个方法。

<表类=“s-表”> <标题> SessionID 用户 创建时间 ID 代码 <正文> 12 MYDOMAIN\用户名 2021-06-28 07:35:54.4321 42 12 2021-06-28 15:35:54.4321 40 0 13 MYDOMAIN\Other.User 2021-06-28 11:12:44.1234 42 13 2021-06-28 13:01:12.5678 40 0

最佳答案

如果您检查示例 XML 记录,您会发现节点的路径不在/EventData/Data 下。这需要一些摆弄,但这对我来说非常有效。

$xmlFilter = @"
<QueryList>
  <Query Id="0" Path="Microsoft-Windows-TerminalServices-LocalSessionManager/Operational">
    <Select Path="Microsoft-Windows-TerminalServices-LocalSessionManager/Operational">*[System[(EventID=40 or EventID=42)]]</Select>
  </Query>
</QueryList>
"@

$SelectorStrings= [String[]]@(
    'Event/UserData/EventXML/User',
    'Event/UserData/EventXML/Session',
    'Event/UserData/EventXML/Reason'
)

Get-WinEvent -FilterXml $xmlFilter | ForEach-Object {

    switch ($_.id){
        40 {$SelectorStrings[1] = 'Event/UserData/EventXML/Session'}
        42 {$SelectorStrings[1] = 'Event/UserData/EventXML/SessionID'}
    }

    $PropertySelector= [System.Diagnostics.Eventing.Reader.EventLogPropertySelector]::new($SelectorStrings)

    $user,$sessionID,$reason = $_.GetPropertyValues($PropertySelector)

    [PSCustomObject]@{
        SessionID   = $sessionID
        User        = $user
        TimeCreated = $_.TimeCreated
        ID          = $_.ID
        Code        = $reason
    }

}

关于powershell - EventLogPropertySelector 未从 PowerShell 中的事件对象返回扩展数据,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/68187149/

相关文章:

XPath "following siblings before"

arrays - PowerShell,Get-WinEvent -FilterHashTable ID 和数组的奇怪行为

powershell - 关于迭代的哈希表与自定义对象数组

powershell - 从Get-ADUser比较数组中的值

xml - XSLT - 如何只保留 XML 中需要的元素

xml - Xpath 选择具有命名空间的同级属性的值

visual-studio-2010 - 如何执行与从Powershell中发布Visual Studio中的发布完全相同的功能

powershell - 如何强制 Powershell 使用新的 Azure 订阅

Powershell - 登录/注销事件 - Get-WinEvent 与 Get-EventLog