如何编写PowerShell脚本获取多台服务器仅文件夹的完整NTFS权限
改进后的PowerShell脚本(多服务器非系统盘文件夹NTFS权限采集)
原脚本存在几个核心问题:
- 提前在本地获取
D:\文件夹列表,所有远程服务器都复用本地路径,完全不符合需求 - 未自动识别远程服务器的非系统盘,仅固定D盘
- 无错误捕获机制,无法排查远程连接、权限不足等问题
- 数组累加
$Output +=性能低下,大文件夹场景会卡顿
以下是修复并优化后的脚本:
# 读取目标服务器列表 $Servers = Get-Content .\Servers.txt # 使用泛型列表提升性能,替代数组累加 $Output = [System.Collections.Generic.List[PSObject]]::new() foreach ($Server in $Servers) { Write-Host "正在处理服务器: $Server" -ForegroundColor Cyan $errorMessage = $null try { # 远程获取服务器的逻辑驱动器,排除系统盘 $drives = Invoke-Command -ComputerName $Server -ScriptBlock { Get-Volume | Where-Object { $_.DriveType -eq 'Fixed' -and $_.DriveLetter -ne $null -and -not $_.SystemVolume } | Select-Object -ExpandProperty DriveLetter } -ErrorAction Stop if (-not $drives) { $errorMessage = "未找到非系统固定磁盘" throw $errorMessage } # 遍历每个非系统盘,递归获取文件夹及其NTFS权限 foreach ($drive in $drives) { $drivePath = "\\$Server\$drive`$" Write-Host " 正在扫描磁盘: $drivePath" -ForegroundColor Gray $folders = Get-ChildItem -Path $drivePath -Recurse -Force -Directory -ErrorAction Stop foreach ($folder in $folders) { try { $acl = Get-Acl -Path $folder.FullName -ErrorAction Stop foreach ($access in $acl.Access) { # 构造输出对象 $outputObj = [PSCustomObject]@{ '服务器' = $Server '文件夹路径' = $folder.FullName '用户/组' = $access.IdentityReference '权限' = $access.FileSystemRights '是否继承' = $access.IsInherited '错误信息' = $null } $Output.Add($outputObj) } } catch { # 捕获单个文件夹的权限获取错误 $outputObj = [PSCustomObject]@{ '服务器' = $Server '文件夹路径' = $folder.FullName '用户/组' = $null '权限' = $null '是否继承' = $null '错误信息' = $_.Exception.Message } $Output.Add($outputObj) Write-Warning " 文件夹 $($folder.FullName) 处理失败: $($_.Exception.Message)" } } } } catch { # 捕获服务器级别的错误(如连接失败、无磁盘等) $outputObj = [PSCustomObject]@{ '服务器' = $Server '文件夹路径' = $null '用户/组' = $null '权限' = $null '是否继承' = $null '错误信息' = $_.Exception.Message } $Output.Add($outputObj) Write-Warning "服务器 $Server 处理失败: $($_.Exception.Message)" } } # 导出结果到CSV $Output | Export-Csv -Path .\NTFSPerm.csv -Encoding UTF8 -NoTypeInformation Write-Host "处理完成,结果已导出到 .\NTFSPerm.csv" -ForegroundColor Green
关键改进说明
- 远程磁盘识别:通过
Invoke-Command在远程服务器上执行Get-Volume,筛选出非系统的固定磁盘,自动适配不同服务器的磁盘配置 - 错误分层捕获:分为服务器连接错误、磁盘扫描错误、单个文件夹权限获取错误,每个错误都记录到输出CSV中,方便后续排查
- 性能优化:使用
[System.Collections.Generic.List[PSObject]]替代数组累加,避免频繁数组扩容带来的性能损耗 - UNC路径访问:使用
\\Server\Drive$的UNC路径访问远程磁盘,确保跨服务器路径有效性 - 编码与格式:导出CSV时指定UTF8编码,避免中文乱码,同时移除类型信息头
使用注意事项
- 执行脚本的账号需要具备目标服务器的管理员权限,才能读取磁盘信息和NTFS权限
- 目标服务器需要启用PowerShell远程管理(默认已启用,若未启用可执行
Enable-PSRemoting -Force开启) Servers.txt文件需每行填写一个服务器名称或IP地址
内容的提问来源于stack exchange,提问作者Puneet Tiwari
相关产品推荐
相关产品推荐

