如何通过PowerShell从安全组中同时获取用户和计算机对象?
实现AD组同时获取用户与计算机对象的脚本修改方案
核心思路
原脚本仅通过Get-ADUser处理组成员,会自动过滤计算机对象。要实现部分组同时拉取用户和计算机,需要:
- 区分目标组(哪些组需要混合拉取,哪些只需要用户)
- 根据成员的
objectClass属性分别处理用户和计算机 - 统一输出结构,保证CSV列一致
修改后的完整脚本
Import-Module ActiveDirectory # 定义需要同时获取用户和计算机的组(可根据实际需求调整过滤规则,比如直接指定组名数组) $mixedGroups = Get-ADGroup -Filter "Name -like 'TST*ALL*'" # 其他仅需获取用户的TST组 $userOnlyGroups = Get-ADGroup -Filter "Name -like 'TST*' -and Name -notlike 'TST*ALL*'" # 处理混合组(用户+计算机) foreach ($group in $mixedGroups) { # 获取组内所有成员 $members = Get-ADGroupMember -Identity $group # 处理用户成员,保留原有的属性提取逻辑 $userData = $members | Where-Object { $_.objectClass -eq 'user' } | Get-ADUser -Properties samaccountname, mail, AccountExpires, manager, employeeid, employeetype | Select-Object @{n="Type";e={"User"}}, samaccountname, mail, employeeid, employeetype, @{l="expiration_date";e={ accountExpiresToString($_.AccountExpires)}}, @{n="Manager Name";e={ if ($_.Manager) { (Get-ADUser -Identity $_.Manager -Properties displayname).DisplayName } else { $null } }} # 处理计算机成员,提取计算机相关属性 $computerData = $members | Where-Object { $_.objectClass -eq 'computer' } | Get-ADComputer -Properties samaccountname, name, operatingSystem, operatingSystemVersion | Select-Object @{n="Type";e={"Computer"}}, samaccountname, @{n="mail";e={ $null }}, @{n="employeeid";e={ $null }}, @{n="employeetype";e={ $null }}, @{n="expiration_date";e={ $null }}, @{n="Manager Name";e={ $null }}, name, operatingSystem, operatingSystemVersion # 合并用户和计算机数据,导出到CSV $userData + $computerData | Export-CSV -Path "C:\tmp\$($group.Name).csv" -NoTypeInformation -Encoding UTF8 } # 处理仅需用户的组(保留原逻辑,新增Type字段便于区分) foreach ($group in $userOnlyGroups) { Get-ADGroupMember -Identity $group | Get-ADUser -Properties samaccountname, mail, AccountExpires, manager, employeeid, employeetype | Select-Object @{n="Type";e={"User"}}, samaccountname, mail, employeeid, employeetype, @{l="expiration_date";e={ accountExpiresToString($_.AccountExpires)}}, @{n="Manager Name";e={ if ($_.Manager) { (Get-ADUser -Identity $_.Manager -Properties displayname).DisplayName } else { $null } }} | Export-CSV -Path "C:\tmp\$($group.Name).csv" -NoTypeInformation -Encoding UTF8 } # 转换AccountExpires字段的辅助函数(如果你的环境中已定义可删除) function accountExpiresToString($accountExpires) { if ($accountExpires -eq 0 -or $accountExpires -eq [Int64]::MaxValue) { "Never Expires" } else { [DateTime]::FromFileTime($accountExpires).ToString("yyyy-MM-dd") } }
关键修改说明
- 组分类逻辑:
- 通过过滤规则拆分
mixedGroups(需混合拉取的组)和userOnlyGroups(仅需用户的组),你也可以直接指定组名数组,比如$mixedGroups = Get-ADGroup -Identity "TST-AllMembers", "TST-DevicesUsers"
- 通过过滤规则拆分
- 成员类型区分:
- 用
Where-Object筛选成员的objectClass属性,分别调用Get-ADUser和Get-ADComputer获取对应类型的属性
- 用
- 输出结构统一:
- 添加
Type字段明确标识记录是用户还是计算机 - 计算机无用户专属字段(如mail、employeeid),用
$null填充,确保CSV列对齐,避免导出报错
- 添加
- 容错优化:
- 处理Manager字段时增加空值判断,避免无经理的用户触发报错
- 补充了
accountExpiresToString函数的完整定义,确保过期日期转换逻辑可用
内容的提问来源于stack exchange,提问作者Arbelac
相关产品推荐
相关产品推荐

