PowerShell域计算机LastLogonTimestamp日志含@{...}冗余字符求助
搞定你的日志格式问题!
你碰到的@{......}冗余字符问题,根源很简单:你把整个PowerShell自定义对象直接传给了Write-EventLog的-Message参数。控制台打印时PowerShell会自动帮你格式化对象输出,但Write-EventLog只会调用对象默认的ToString()方法,这就导致了这种键值对格式的字符串,自然让SIEM没法正常解析。
下面给你两个关键修改,不仅解决格式问题,还能优化脚本性能:
1. 直接提取日期值,别传对象
不要再用Select-Object创建新的自定义对象,直接把LastLogonTimestamp转换成友好的日期字符串,然后传给日志消息。
2. 减少AD查询次数(必做优化)
你原来的脚本在循环里重复调用Get-ADComputer,完全没必要——第一次查询时就把LastLogonTimestamp属性一起拉回来,省得反复折腾AD服务器。
修改后的完整脚本
# 一次性获取所有需要的属性,避免重复查询AD $dcs = Get-ADComputer -Filter { OperatingSystem -NotLike '*Server*' } -Properties OperatingSystem, LastLogonTimestamp foreach($dc in $dcs) { # 创建事件源(忽略已存在的情况) try { [System.Diagnostics.EventLog]::CreateEventSource($dc.Name, "System") } catch { # 啥也不用做,已经存在就跳过 } # 直接把AD返回的时间戳转成可读的DateTime $lastLogonDate = [DateTime]::FromFileTime($dc.LastLogonTimeStamp) # 调试用,确认输出正确(满意后可以注释掉) Write-Host "$($dc.Name) 的最后登录时间:$lastLogonDate" # 写入系统日志,这次传的是纯日期字符串 Write-EventLog -LogName System -Source $dc.Name -EventID 8007 -EntryType Information -Message "LastLogonTimeStamp`n$lastLogonDate" -Category 1 }
为啥这么改?
- 合并AD查询:第一次
Get-ADComputer就带上LastLogonTimestamp,循环里不用再查一次,既快又减轻AD服务器负担。 - 避免对象转字符串坑:直接把时间戳转成
DateTime对象,PowerShell会自动把它转换成人类友好的字符串(比如2024/05/20 下午2:30),再也不会出现@{...}这种奇怪格式。 - 调试输出更清晰:用
Write-Host打印计算机名和对应时间,方便你确认数据是否正确。
改完之后,你再看系统日志,消息里就是干净的日期字符串,SIEM就能正常处理啦!
内容的提问来源于stack exchange,提问作者rickbond
相关产品推荐
相关产品推荐

