如何使用PnP-PowerShell撤销SharePoint Online文件的共享链接?
原脚本低效根源
- 每处理一个文件就发起多次
ExecuteQuery()请求,网络往返次数过多,拖慢整体速度 - 逐个加载权限分配和成员对象,没有利用批量加载机制
- 遍历所有文件,未过滤仅存在共享链接的文件,做了大量无用功
- 每个站点重复交互式登录,增加操作冗余
方案一:优化后的PnP PowerShell脚本
通过批量加载、减少API请求、精准过滤目标文件来提升效率:
# 全局交互式登录一次,后续站点复用上下文 Connect-PnPOnline -Url https://tenant.sharepoint.com -Interactive $SiteURLs = @("https://tenant.sharepoint.com/sites/site1", "https://tenant.sharepoint.com/sites/site2") foreach ($SiteURL in $SiteURLs) { # 切换站点上下文,无需重复登录 Connect-PnPOnline -Url $SiteURL -UseWebLogin # 获取所有文档库 $documentLibraries = Get-PnPList | Where-Object { $_.BaseTemplate -eq 101 } foreach ($lib in $documentLibraries) { Write-Host "正在处理文档库:$($lib.Title)" -ForegroundColor Cyan # 仅获取有共享链接的文件,减少遍历范围 $filesWithLinks = Get-PnPListItem -List $lib -Fields "ID", "FileRef" | ForEach-Object { $sharingLinks = Get-PnPSharingLink -List $lib -ItemId $_.ID if ($sharingLinks.Count -gt 0) { $_ } } foreach ($file in $filesWithLinks) { # 删除该文件所有共享链接 Remove-PnPSharingLink -List $lib -ItemId $file.ID -All Write-Host "已撤销文件:$($file["FileRef"])" -ForegroundColor Green } } }
优化说明
- 全局登录一次,切换站点用
-UseWebLogin复用凭据,避免重复交互式认证 - 用
Get-PnPSharingLink精准获取有共享链接的文件,减少无效遍历 - 直接调用
Remove-PnPSharingLink -All批量删除单个文件的所有共享链接,无需逐个处理权限分配
方案二:使用Microsoft Graph API批量处理(超大量文件首选)
Graph API支持批量请求和分页查询,处理十万级以上文件时效率远高于PnP:
# 连接Graph API,需授予Files.ReadWrite.All、Sites.ReadWrite.All权限 Connect-MgGraph -Scopes "Files.ReadWrite.All", "Sites.ReadWrite.All" $SiteURLs = @("https://tenant.sharepoint.com/sites/site1", "https://tenant.sharepoint.com/sites/site2") foreach ($SiteURL in $SiteURLs) { # 获取站点ID $site = Get-MgSite -Filter "webUrl eq '$SiteURL'" if (-not $site) { Write-Host "未找到站点:$SiteURL" -ForegroundColor Red continue } # 获取站点下所有文档库 $documentLibraries = Get-MgSiteDrive -SiteId $site.Id | Where-Object { $_.DriveType -eq "documentLibrary" } foreach ($lib in $documentLibraries) { Write-Host "正在处理文档库:$($lib.Name)" -ForegroundColor Cyan # 分页获取库内所有文件 $files = Get-MgDriveItemChild -DriveId $lib.Id -All -Filter "file ne null" foreach ($file in $files) { # 获取文件的共享链接 $sharingLinks = Get-MgDriveItemPermission -DriveId $lib.Id -DriveItemId $file.Id | Where-Object { $_.Link -ne $null } foreach ($link in $sharingLinks) { # 删除共享链接 Remove-MgDriveItemPermission -DriveId $lib.Id -DriveItemId $file.Id -PermissionId $link.Id Write-Host "已撤销文件 $($file.Name) 的共享链接" -ForegroundColor Green } } } }
进阶优化:Graph批量请求
如果文件量极大,可使用Graph批量请求接口,将多个删除操作打包成一个请求,进一步减少网络开销:
# 构建批量请求体 $batchRequests = @() $requestId = 0 # 收集所有需要删除的共享链接权限ID foreach ($file in $files) { $sharingLinks = Get-MgDriveItemPermission -DriveId $lib.Id -DriveItemId $file.Id | Where-Object { $_.Link -ne $null } foreach ($link in $sharingLinks) { $batchRequests += @{ id = $requestId++ method = "DELETE" url = "/drives/$($lib.Id)/items/$($file.Id)/permissions/$($link.Id)" } } } # 发送批量请求 $batchBody = @{ requests = $batchRequests } Invoke-MgGraphRequest -Method Post -Uri "https://graph.microsoft.com/v1.0/$batch" -Body $batchBody -ContentType "application/json"
内容的提问来源于stack exchange,提问作者Jignesh Chauhan
相关产品推荐
相关产品推荐

