请求协助排查PowerShell空DL检测脚本问题并合并脚本
问题分析与解决方案
首先得拆解你遇到的两个核心问题:
- 第一个脚本误把只有1个成员的通讯组判定为空组——这是PowerShell处理单个对象和数组的
Count属性时的常见“坑”; - 第二个脚本没有输出,大概率是因为第一个脚本导出的CSV里混进了实际有成员的组,再加上脚本没处理好单个成员的查询逻辑。
问题根源解释
当Get-DistributionGroupMember返回单个成员时,它输出的是一个单独的对象,而非数组。这个单独的对象没有.Count属性(或者说.Count返回$null),你的第一个脚本里!(Get-DistributionGroupMember ...).Count会把$null取反为$true,导致这些单成员组被错误标记为空组。
方案1:合并为一个脚本(推荐)
这个脚本会一次性完成检测、筛选和导出,直接输出所有空组和单成员组的详细信息,避免分两步的麻烦:
Get-DistributionGroup -ResultSize Unlimited | ForEach-Object { $currentGroup = $_ # 获取组成员,忽略可能的错误(比如组不存在) $groupMembers = Get-DistributionGroupMember -Identity $currentGroup.PrimarySmtpAddress -ErrorAction SilentlyContinue # 正确计算成员数量:处理空、单个、多个成员的情况 $memberCount = switch ($groupMembers) { $null { 0 } { $_ -is [array] } { $_.Count } default { 1 } } # 只筛选空组或单成员组 if ($memberCount -le 1) { if ($memberCount -eq 0) { # 空组,输出组信息,成员部分标注 [PSCustomObject]@{ 组显示名称 = $currentGroup.DisplayName 组SMTP地址 = $currentGroup.PrimarySmtpAddress 成员显示名称 = "无成员" 成员SMTP地址 = "无成员" } } else { # 单成员组,输出组和成员的对应信息 $groupMembers | ForEach-Object { [PSCustomObject]@{ 组显示名称 = $currentGroup.DisplayName 组SMTP地址 = $currentGroup.PrimarySmtpAddress 成员显示名称 = $_.DisplayName 成员SMTP地址 = $_.PrimarySmtpAddress } } } } } | Export-Csv -Path "空组及单成员组明细.csv" -NoTypeInformation -Encoding UTF8
这个脚本的优势:
- 自动处理空组、单成员组、多成员组的判断逻辑,不会出现误判
- 直接输出组和成员的对应关系,CSV里的信息更直观
- 一步到位,不需要手动导出再导入查询
方案2:修复你的两个独立脚本
如果你还是想保留分两步的方式,可以先修复第一个脚本的筛选逻辑,再调整第二个脚本的查询逻辑:
第一步:修复第一个脚本,导出真正的空组和单成员组
Get-DistributionGroup -ResultSize Unlimited | ForEach-Object { $members = Get-DistributionGroupMember -Identity $_.PrimarySmtpAddress -ErrorAction SilentlyContinue $memberCount = switch ($members) { $null { 0 } { $_ -is [array] } { $_.Count } default { 1 } } # 导出成员数≤1的组 if ($memberCount -le 1) { $_ | Select-Object DisplayName, PrimarySmtpAddress } } | Export-Csv -Path "待检查的DL.csv" -NoTypeInformation -Encoding UTF8
第二步:修复第二个脚本,正确读取并查询成员
Import-Csv -Path "待检查的DL.csv" | ForEach-Object { $groupSMTP = $_.PrimarySmtpAddress $members = Get-DistributionGroupMember -Identity $groupSMTP -ErrorAction SilentlyContinue if ($null -eq $members) { # 空组,输出标记 [PSCustomObject]@{ 组SMTP地址 = $groupSMTP 成员显示名称 = "无成员" } } else { # 处理单个或多个成员(即使是单个对象,ForEach-Object也能遍历) $members | ForEach-Object { [PSCustomObject]@{ 组SMTP地址 = $groupSMTP 成员显示名称 = $_.DisplayName } } } } | Export-Csv -Path "成员明细.csv" -NoTypeInformation -Encoding UTF8
修复点说明:
- 第一个脚本现在能正确识别单成员组,不会误导出
- 第二个脚本添加了错误处理,避免因组不存在导致中断,同时处理了空组的情况,确保所有待检查的组都有输出
内容的提问来源于stack exchange,提问作者Schmit
相关产品推荐
相关产品推荐

