Microsoft Graph PowerShell 群組型授權範例
Microsoft Entra ID 中的群組型授權 (Microsoft Entra 的一部分) 可透過 Azure 入口網站取得。 有一些實用的工作可以使用 Microsoft Graph PowerShell Cmdlet 來執行。
在本文中,我們會使用 Microsoft Graph PowerShell 來探討一些範例。
注意
自 2024 年 3 月 30 日起,Azure AD 和 MSOnline PowerShell 模組已被淘汰。 若要深入了解,請閱讀淘汰更新。 在此日期之後,對這些模組的支援僅限於對 Microsoft Graph PowerShell SDK 的移轉協助和安全性修正。 淘汰的模組將繼續運作至 2025 年 3 月 30 日。
我們建議移轉至 Microsoft Graph PowerShell 以與 Microsoft Entra ID (以前稱為 Azure AD) 互動。 如需了解常見的移轉問題,請參閱移轉常見問題。 注意:MSOnline 1.0.x 版可能會在 2024 年 6 月 30 日之後發生中斷。
警告
這些範例僅供示範用途。 建議您先在較小型規模或個別的測試環境中進行測試後,才在生產環境中依賴這些範例。 您可能也需要修改範例,以符合特定環境的需求。
在開始執行 Cmdlet 之前,請先確定您已藉由執行 Connect-MgGraph
cmdlet- 來連線到組織。
指派授權至群組
群組型授權提供方便的方式來管理授權指派。 您可以將一或多個產品授權指派給群組,並將這些授權指派給群組的所有成員。
# Import the Microsoft.Graph.Groups module
Import-Module Microsoft.Graph.Groups
$groupId = "911f05cf-f635-440c-b888-e54c73e0ef1a"
# Create a hashtable to store the parameters for the Set-MgGroupLicense cmdlet
$params = @{
AddLicenses = @(
@{
# Remove the DisabledPlans key as we don't need to disable any service plans
# Specify the SkuId of the license you want to assign
SkuId = "c42b9cae-ea4f-4ab7-9717-81576235ccac"
}
)
# Keep the RemoveLicenses key empty as we don't need to remove any licenses
RemoveLicenses = @(
)
}
# Call the Set-MgGroupLicense cmdlet to update the licenses for the specified group
# Replace $groupId with the actual group ID
Set-MgGroupLicense -GroupId $groupId -BodyParameter $params
檢視指派給群組的產品授權
Get-MgGroup -GroupId 99c4216a-56de-42c4-a4ac-1111cd8c7c41 -Property "AssignedLicenses" | Select-Object -ExpandProperty AssignedLicenses
檢視指派給群組的所有已停用服務方案授權
Get-MgGroup -GroupId 1ad75eeb-7e5a-4367-a493-9214d90d54d0 -Property "AssignedLicenses" |
Select-Object -ExpandProperty AssignedLicenses |
ForEach-Object {
$_ | Select-Object SkuId, DisabledPlans
}
取得具有授權的所有群組
# Import the Microsoft.Graph.Groups module
Import-Module Microsoft.Graph.Groups
# Get all groups and licenses
$groups = Get-MgGroup -All
$groupsWithLicenses = @()
# Loop through each group and check if it has any licenses assigned
foreach ($group in $groups) {
$licenses = Get-MgGroup -GroupId $group.Id -Property "AssignedLicenses, Id, DisplayName" | Select-Object AssignedLicenses, DisplayName, Id
if ($licenses.AssignedLicenses) {
$groupData = [PSCustomObject]@{
ObjectId = $group.Id
DisplayName = $group.DisplayName
Licenses = $licenses.AssignedLicenses
}
$groupsWithLicenses += $groupData
}
}
取得具有授權之群組的統計資料
# Import User Graph Module
Import-Module Microsoft.Graph.Users
# Authenticate to MS Graph
Connect-MgGraph -Scopes "User.Read.All", "Directory.Read.All", "Group.ReadWrite.All"
#get all groups with licenses
$groups = Get-MgGroup -All -Property LicenseProcessingState, DisplayName, Id, AssignedLicenses | Select-Object displayname, Id, LicenseProcessingState, AssignedLicenses | Select-Object DisplayName, Id, AssignedLicenses -ExpandProperty LicenseProcessingState | Select-Object DisplayName, State, Id, AssignedLicenses | Where-Object {$_.State -eq "ProcessingComplete"}
$groupInfoArray = @()
# Filter the groups to only include those that have licenses assigned
$groups = $groups | Where-Object {$_.AssignedLicenses -ne $null}
# For each group, get the group name, license types, total user count, licensed user count, and license error count
foreach ($group in $groups) {
$groupInfo = New-Object PSObject
$groupInfo | Add-Member -MemberType NoteProperty -Name "Group Name" -Value $group.DisplayName
$groupInfo | Add-Member -MemberType NoteProperty -Name "Group ID" -Value $group.Id
$groupInfo | Add-Member -MemberType NoteProperty -Name "License Types" -Value ($group.AssignedLicenses | Select-Object -ExpandProperty SkuId)
$groupInfo | Add-Member -MemberType NoteProperty -Name "Total User Count" -Value (Get-MgGroupMember -GroupId $group.Id -All | Measure-Object).Count
$groupInfo | Add-Member -MemberType NoteProperty -Name "Licensed User Count" -Value (Get-MgGroupMember -GroupId $group.Id -All | Where-Object {$_. LicenseProcessingState -eq "ProcessingComplete"} | Measure-Object).Count
$groupInfo | Add-Member -MemberType NoteProperty -Name "License Error Count" -Value (Get-MgGroupMember -GroupId $group.Id -All | Where-Object {$_.LicenseProcessingState -eq "ProcessingFailed"} | Measure-Object).Count
$groupInfoArray += $groupInfo
}
# Format the output and print it to the console
$groupInfoArray | Format-Table -AutoSize
取得具有授權錯誤的所有群組
# Import User Graph Module
Import-Module Microsoft.Graph.Users
# Authenticate to MS Graph
Connect-MgGraph -Scopes "Group.Read.All"
# Get all groups in the tenant with license assigned and with errors
$groups = Get-MgGroup -All -Property LicenseProcessingState, DisplayName, Id, AssignedLicenses | Select-Object displayname, Id, LicenseProcessingState, AssignedLicenses | Select-Object DisplayName, Id, AssignedLicenses -ExpandProperty LicenseProcessingState | Select-Object DisplayName, State, Id, AssignedLicenses | Where-Object {$_.State -eq "ProcessingFailed" -and $_.AssignedLicenses -ne $null }
# Display the results and format output
$groups | Format-Table -AutoSize
取得群組中具有授權錯誤的所有使用者
若群組中包含某些授權相關錯誤,您現在可以列出這些錯誤所影響到的使用者。 使用者也可能有來自其他群組的錯誤。 不過,此範例所列出的結果僅限於與有問題之群組有關的錯誤,其方法是對使用者每個 IndirectLicenseError 項目的 ReferencedObjectId 屬性進行檢查。
# Import User Graph Module
Import-Module Microsoft.Graph.Users
# Authenticate to MS Graph
Connect-MgGraph -Scopes "Group.Read.All", "User.Read.All"
# Get all groups in the tenant with license assigned
$groups = Get-MgGroup -All -Property LicenseProcessingState, DisplayName, Id, AssignedLicenses | Select-Object displayname, Id, LicenseProcessingState, AssignedLicenses | Select-Object DisplayName, Id, AssignedLicenses | Where-Object {$_.AssignedLicenses -ne $null }
#output array
$groupInfoArray = @()
# Get All Members from the groups and check their license status
foreach($group in $groups) {
$groupMembers = Get-MgGroupMember -GroupId $group.Id -All -Property LicenseProcessingState, DisplayName, Id, AssignedLicenses | Select-Object displayname, Id, LicenseProcessingState, AssignedLicenses | Select-Object DisplayName, Id, AssignedLicenses -ExpandProperty LicenseProcessingState | Select-Object DisplayName, Id, AssignedLicenses | Where-Object {$_.AssignedLicenses -ne $null }
foreach($member in $groupMembers) {
Write-Host "Member $($member.DisplayName)"
if($member.LicenseProcessingState -eq "ProcessingFailed") {
$group | Add-Member -MemberType NoteProperty -Name "License Error" -Value $member.DisplayName
$groupInfoArray += $group
}
}
}
# Format the output and print it to the console
if ($groupInfoArray.Length -gt 0) {
$groupInfoArray | Format-Table -AutoSize
}
else {
Write-Host "No License Errors"
}
取得整個組織中具有授權錯誤的所有使用者
下列指令碼可用來取得具有一或多個群組之授權錯誤的所有使用者。 此指令碼會將每位使用者的每個授權錯誤各列印在一個資料列中,以方便您清楚識別每個錯誤的來源。
# Import User Graph Module
Import-Module Microsoft.Graph.Users
# Authenticate to MS Graph
Connect-MgGraph -Scopes "User.Read.All"
# Get All Users From the Tenant with licenses assigned
$users = Get-MgUser -All -Property AssignedLicenses, LicenseAssignmentStates, DisplayName | Select-Object DisplayName, AssignedLicenses -ExpandProperty LicenseAssignmentStates | Select-Object DisplayName, AssignedByGroup, State, Error, SkuId
#count the number of users found with errors
$count = 0
# Loop through each user and check the Error property for None value
foreach($user in $users) {
if($user.Error -ne "None") {
$count += 1
Write-Host "User $($user.DisplayName) has a license error"
}
}
if ($count -le 0) {
write-host "No user found with license errors"
}
檢查使用者的授權是透過直接指派還是群組繼承而得到
# Connect to Microsoft Graph using Connect-MgGraph
Connect-MgGraph -Scopes "User.Read.All", "Group.Read.All"
# Get all users using Get-MgUser with a filter
$users = Get-MgUser -All -Property AssignedLicenses, LicenseAssignmentStates, DisplayName | Select-Object DisplayName, AssignedLicenses -ExpandProperty LicenseAssignmentStates | Select-Object DisplayName, AssignedByGroup, State, Error, SkuId
$output = @()
# Loop through all users and get the AssignedByGroup Details which will list the groupId
foreach ($user in $users) {
# Get the group ID if AssignedByGroup is not empty
if ($user.AssignedByGroup -ne $null)
{
$groupId = $user.AssignedByGroup
$groupName = Get-MgGroup -GroupId $groupId | Select-Object -ExpandProperty DisplayName
Write-Host "$($user.DisplayName) is assigned by group - $($groupName)" -ErrorAction SilentlyContinue -ForegroundColor Yellow
$result = [pscustomobject]@{
User=$user.DisplayName
AssignedByGroup=$true
GroupName=$groupName
GroupId=$groupId
}
$output += $result
}
else {
$result = [pscustomobject]@{
User=$user.DisplayName
AssignedByGroup=$false
GroupName="NA"
GroupId="NA"
}
$output += $result
Write-Host "$($user.DisplayName) is Not assigned by group" -ErrorAction SilentlyContinue -ForegroundColor Cyan
}
}
# Display the result
$output | ft
移除具有群組授權之使用者的直接授權
此指令碼的目的,是要為已從群組繼承了相同授權的使用者,移除不必要的直接授權;例如,在轉換為群組型授權的過程中進行此操作。
注意
為了確保使用者不會失去服務和資料的存取權,請務必確認直接指派的授權不會提供比繼承授權更多的服務功能。 目前無法使用 PowerShell 來判斷哪些服務是透過繼承的授權與直接授權來啟用。 因此,指令碼會使用已知繼承自群組的最低服務層級,來檢查並確保使用者不會發生非預期的服務遺失。
變數
- $groupLicenses:代表指派給群組的授權。
- $groupMembers:包含群組的成員。
- $userLicenses:保留直接指派給使用者的授權。
- $licensesToRemove:儲存需要從使用者移除的授權。
# Import the Microsoft.Graph.Users and Microsoft.Graph.Groups modules
Import-Module Microsoft.Graph.Users -Force
Import-Module Microsoft.Graph.Authentication -Force
Import-Module Microsoft.Graph.Users.Actions -Force
Import-Module Microsoft.Graph.Groups -Force
Clear-Host
# Connect to Microsoft Graph if not already connected
if ($null -eq (Get-MgContext)) {
Connect-MgGraph -Scopes "Directory.Read.All, User.Read.All, Group.Read.All, Organization.Read.All" -NoWelcome
}
# Get all groups with licenses assigned
$groupsWithLicenses = Get-MgGroup -All -Property AssignedLicenses, DisplayName, Id | Where-Object { $_.assignedlicenses } | Select-Object DisplayName, Id -ExpandProperty AssignedLicenses | Select-Object DisplayName, Id, SkuId
$output = @()
# Check if there are any groups with licenses assigned
if ($null -ne groupsWithLicenses) { foreach (group in $groupsWithLicenses) {
# Get the group's licenses
$groupLicenses = $group.SkuId
# Get the group's members
$groupMembers = Get-MgGroupMember -GroupId $group.Id -All
if ($groupMembers) {
foreach ($member in $groupMembers) {
# Check if the member is a user
if ($member.AdditionalProperties.'@odata.type' -eq '#microsoft.graph.user') {
Write-Host "Fetching license details for $($member.AdditionalProperties.displayName)" -ForegroundColor Yellow
# Get User With Directly Assigned Licenses Only
$user = Get-MgUser -UserId $member.Id -Property AssignedLicenses, LicenseAssignmentStates, DisplayName | Select-Object DisplayName, AssignedLicenses -ExpandProperty LicenseAssignmentStates | Select-Object DisplayName, AssignedByGroup, State, Error, SkuId | Where-Object { $_.AssignedByGroup -eq $null }
$licensesToRemove = @()
if ($user) {
if ($user.count -ge 2) {
foreach ($u in $user) {
$userLicenses = $u.SkuId
$licensesToRemove += $userLicenses | Where-Object { $_ -in $groupLicenses }
}
else {
Write-Host "No conflicting licenses found for the user $($member.AdditionalProperties.displayName)" -ForegroundColor Green
}
# Remove the licenses from the user
if ($licensesToRemove) {
Write-Host "Removing the license $($licensesToRemove) from user $($member.AdditionalProperties.displayName) as inherited from group $($group.DisplayName)" -ForegroundColor Green
$result = Set-MgUserLicense -UserId $member.Id -AddLicenses @() -RemoveLicenses $licensesToRemove
$obj = [PSCustomObject]@{
User = $result.DisplayName
Id = $result.Id
LicensesRemoved = $licensesToRemove
LicenseInheritedFromGroup = $group.DisplayName
GroupId = $group.Id
}
$output += $obj
}
else {
Write-Host "No action required for $($member.AdditionalProperties.displayName)" -ForegroundColor Green
}
}
}
}
else {
Write-Host "The licensed group $($group.DisplayName) has no members, exiting now!!" -ForegroundColor Yellow
}
}
$output | Format-Table -AutoSize
}
else {
Write-Host "No groups found with licenses assigned." -ForegroundColor Cyan
}
下一步
若要深入了解透過群組管理授權的功能集,請參閱下列文章: