-
Notifications
You must be signed in to change notification settings - Fork 23
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Add User Sponsor command #1348
Open
DButoyez
wants to merge
26
commits into
main
Choose a base branch
from
dbutoyi/user_sponsor
base: main
Could not load branches
Branch not found: {{ refName }}
Loading
Could not load tags
Nothing to show
Loading
Are you sure you want to change the base?
Some commits from the old base branch may be removed from the timeline,
and old review comments may become outdated.
Open
Add User Sponsor command #1348
Changes from all commits
Commits
Show all changes
26 commits
Select commit
Hold shift + click to select a range
7339fc6
add user sponsor tests
520dd75
Merge branch 'main' into dbutoyi/user_sponsor
3a5a50c
refactor Get entra user sponsor functions
7d5d535
refactor tests
7bfaefb
refactor and fix unit tests
f3e8c21
import the correct module Entra Beta Users
56e7854
refactor user sponsor beta tests
0d46e96
refactor user sponsor beta test
abbe5c6
Merge branch 'main' into dbutoyi/user_sponsor
b27551e
add documentation for usersponsor command
2a58b06
remove empty doc
c301c74
Merge branch 'main' into dbutoyi/user_sponsor
SteveMutungi254 79c863b
add aliases help messages and refactor
c531c12
Docs enhancements suggestions (#1363)
SteveMutungi254 6542057
refactors remove unsupported search query
74ab937
doc add get by sponsor Id
45a4d0d
Merge branch 'main' into dbutoyi/user_sponsor
SteveMutungi254 c4033f7
Update module/Entra/Microsoft.Entra/Users/Get-EntraUserSponsor.ps1
DButoyez fdb44be
Update module/Entra/Microsoft.Entra/Users/Get-EntraUserSponsor.ps1
DButoyez 0032b1b
Update module/EntraBeta/Microsoft.Entra.Beta/Users/Get-EntraBetaUserS…
DButoyez 1f370a5
Update module/EntraBeta/Microsoft.Entra.Beta/Users/Get-EntraBetaUserS…
DButoyez f3b3fd1
Update module/EntraBeta/Microsoft.Entra.Beta/Users/Get-EntraBetaUserS…
DButoyez 09b141c
Update module/EntraBeta/Microsoft.Entra.Beta/Users/Get-EntraBetaUserS…
DButoyez a7870a7
Update module/docs/entra-powershell-beta/Users/Get-EntraBetaUserSpons…
DButoyez 5e8ec48
Update module/docs/entra-powershell-v1.0/Users/Get-EntraUserSponsor.md
DButoyez 40f2c0c
Update module/docs/entra-powershell-v1.0/Users/Get-EntraUserSponsor.md
SteveMutungi254 File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
104 changes: 104 additions & 0 deletions
104
module/Entra/Microsoft.Entra/Users/Get-EntraUserSponsor.ps1
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,104 @@ | ||
function Get-EntraUserSponsor { | ||
[CmdletBinding(DefaultParameterSetName = 'GetQuery')] | ||
param ( | ||
[Parameter(ParameterSetName = "GetQuery", ValueFromPipeline = $true, ValueFromPipelineByPropertyName = $true, HelpMessage = "Filter to apply to the query.")] | ||
[System.String] $Filter, | ||
|
||
[Parameter(Mandatory = $true, ValueFromPipeline = $true, ValueFromPipelineByPropertyName = $true, HelpMessage = "The unique identifier (User ID) of the user whose sponsor information you want to retrieve.")] | ||
[System.String] $UserId, | ||
|
||
[Alias('Limit')] | ||
[Parameter(ParameterSetName = "GetQuery", ValueFromPipeline = $true, ValueFromPipelineByPropertyName = $true, HelpMessage = "Maximum number of results to return.")] | ||
[System.Nullable`1[System.Int32]] $Top, | ||
|
||
[Parameter(ParameterSetName = "GetQuery", ValueFromPipeline = $true, ValueFromPipelineByPropertyName = $true, HelpMessage = "Retrieve all user's sponsors.")] | ||
[switch] $All, | ||
|
||
[Alias('DirectoryObjectId')] | ||
[Parameter(ParameterSetName = "GetById", Mandatory = $false, ValueFromPipeline = $true, ValueFromPipelineByPropertyName = $true, HelpMessage = "The User Sponsor ID to retrieve.")] | ||
[System.String] $SponsorId, | ||
|
||
[Alias('Select')] | ||
[Parameter(Mandatory = $false, ValueFromPipeline = $false, ValueFromPipelineByPropertyName = $true, HelpMessage = "Properties to include in the results.")] | ||
[System.String[]] $Property | ||
) | ||
|
||
PROCESS { | ||
$customHeaders = New-EntraCustomHeaders -Command $MyInvocation.MyCommand | ||
$params = @{} | ||
$topCount = $null | ||
$baseUri = "https://graph.microsoft.com/v1.0/users/$UserId/sponsors" | ||
$properties = '$select=*' | ||
$params["Method"] = "GET" | ||
$params["Uri"] = "$baseUri/?$properties" | ||
if ($null -ne $PSBoundParameters["Property"]) { | ||
$selectProperties = $PSBoundParameters["Property"] | ||
$selectProperties = $selectProperties -Join ',' | ||
$properties = "`$select=$($selectProperties)" | ||
$params["Uri"] = "$baseUri/?$properties" | ||
} | ||
if ($PSBoundParameters.ContainsKey("Top")) { | ||
$topCount = $PSBoundParameters["Top"] | ||
if ($topCount -gt 999) { | ||
$params["Uri"] += "&`$top=999" | ||
} | ||
else { | ||
$params["Uri"] += "&`$top=$topCount" | ||
} | ||
} | ||
if ($null -ne $PSBoundParameters["SponsorId"]) { | ||
$params["Uri"] += "&`$filter=id eq '$SponsorId'" | ||
} | ||
if ($null -ne $PSBoundParameters["Filter"]) { | ||
$Filter = $PSBoundParameters["Filter"] | ||
$f = '$' + 'Filter' | ||
$params["Uri"] += "&$f=$Filter" | ||
} | ||
Write-Debug("============================ TRANSFORMATIONS ============================") | ||
$params.Keys | ForEach-Object {"$_ : $($params[$_])" } | Write-Debug | ||
Write-Debug("=========================================================================`n") | ||
$response = Invoke-GraphRequest -Headers $customHeaders -Uri $($params.Uri) -Method GET | ConvertTo-Json -Depth 10 | ConvertFrom-Json | ||
try { | ||
$data = $response.value | ConvertTo-Json -Depth 10 | ConvertFrom-Json | ||
$directoryObjectList = @() | ||
$all = $All.IsPresent | ||
$increment = $topCount - $data.Count | ||
|
||
while ($response.'@odata.nextLink' -and (($all -and ($increment -lt 0)) -or $increment -gt 0)) { | ||
$params["Uri"] = $response.'@odata.nextLink' | ||
if ($increment -gt 0) { | ||
$topValue = [Math]::Min($increment, 999) | ||
$params["Uri"] = $params["Uri"].Replace('$top=999', "`$top=$topValue") | ||
$increment -= $topValue | ||
} | ||
$response = Invoke-GraphRequest -Headers $customHeaders -Uri $URI -Method $Method | ConvertTo-Json -Depth 10 | ConvertFrom-Json | ||
$data += $response.value | ConvertTo-Json -Depth 10 | ConvertFrom-Json | ||
} | ||
} catch {} | ||
|
||
foreach ($item in $data) { | ||
if ($null -ne $item) { | ||
# Determine the type based on @odata.type | ||
switch ($item.'@odata.type') { | ||
'#microsoft.graph.user' { | ||
$directoryObject = [Microsoft.Graph.PowerShell.Models.MicrosoftGraphUser]::new() | ||
} | ||
'#microsoft.graph.group' { | ||
$directoryObject = [Microsoft.Graph.PowerShell.Models.MicrosoftGraphGroup]::new() | ||
} | ||
default { | ||
Write-Warning "Unknown type: $($item.'@odata.type')" | ||
continue | ||
} | ||
} | ||
$item.PSObject.Properties | ForEach-Object { | ||
$propertyName = $_.Name | ||
$propertyValue = $_.Value | ||
$directoryObject | Add-Member -MemberType NoteProperty -Name $propertyName -Value $propertyValue -Force | ||
} | ||
$directoryObjectList += $directoryObject | ||
} | ||
} | ||
$directoryObjectList | ||
} | ||
} |
104 changes: 104 additions & 0 deletions
104
module/EntraBeta/Microsoft.Entra.Beta/Users/Get-EntraBetaUserSponsor.ps1
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,104 @@ | ||
function Get-EntraBetaUserSponsor { | ||
[CmdletBinding(DefaultParameterSetName = 'GetQuery')] | ||
param ( | ||
[Parameter(ParameterSetName = "GetQuery", ValueFromPipeline = $true, ValueFromPipelineByPropertyName = $true, HelpMessage = "Filter to apply to the query.")] | ||
[System.String] $Filter, | ||
|
||
[Parameter(Mandatory = $true, ValueFromPipeline = $true, ValueFromPipelineByPropertyName = $true, HelpMessage = "The unique identifier (User ID) of the user whose sponsor information you want to retrieve.")] | ||
[System.String] $UserId, | ||
|
||
[Alias('Limit')] | ||
[Parameter(ParameterSetName = "GetQuery", ValueFromPipeline = $true, ValueFromPipelineByPropertyName = $true, HelpMessage = "Maximum number of results to return.")] | ||
[System.Nullable`1[System.Int32]] $Top, | ||
|
||
[Parameter(ParameterSetName = "GetQuery", ValueFromPipeline = $true, ValueFromPipelineByPropertyName = $true, HelpMessage = "Retrieve all user's sponsors.")] | ||
[switch] $All, | ||
|
||
[Alias('DirectoryObjectId')] | ||
[Parameter(ParameterSetName = "GetById", Mandatory = $false, ValueFromPipeline = $true, ValueFromPipelineByPropertyName = $true, HelpMessage = "The User Sponsor ID to retrieve.")] | ||
[System.String] $SponsorId, | ||
|
||
[Alias('Select')] | ||
[Parameter(Mandatory = $false, ValueFromPipeline = $false, ValueFromPipelineByPropertyName = $true, HelpMessage = "Properties to include in the results.")] | ||
[System.String[]] $Property | ||
) | ||
|
||
PROCESS { | ||
$customHeaders = New-EntraBetaCustomHeaders -Command $MyInvocation.MyCommand | ||
$params = @{} | ||
$topCount = $null | ||
$baseUri = "https://graph.microsoft.com/beta/users/$UserId/sponsors" | ||
$properties = '$select=*' | ||
$params["Method"] = "GET" | ||
$params["Uri"] = "$baseUri/?$properties" | ||
if ($null -ne $PSBoundParameters["Property"]) { | ||
$selectProperties = $PSBoundParameters["Property"] | ||
$selectProperties = $selectProperties -Join ',' | ||
$properties = "`$select=$($selectProperties)" | ||
$params["Uri"] = "$baseUri/?$properties" | ||
} | ||
if ($PSBoundParameters.ContainsKey("Top")) { | ||
$topCount = $PSBoundParameters["Top"] | ||
if ($topCount -gt 999) { | ||
$params["Uri"] += "&`$top=999" | ||
} | ||
else { | ||
$params["Uri"] += "&`$top=$topCount" | ||
} | ||
} | ||
if ($null -ne $PSBoundParameters["SponsorId"]) { | ||
$params["Uri"] += "&`$filter=id eq '$SponsorId'" | ||
} | ||
if ($null -ne $PSBoundParameters["Filter"]) { | ||
$Filter = $PSBoundParameters["Filter"] | ||
$f = '$' + 'Filter' | ||
$params["Uri"] += "&$f=$Filter" | ||
} | ||
Write-Debug("============================ TRANSFORMATIONS ============================") | ||
$params.Keys | ForEach-Object {"$_ : $($params[$_])" } | Write-Debug | ||
Write-Debug("=========================================================================`n") | ||
$response = Invoke-GraphRequest -Headers $customHeaders -Uri $($params.Uri) -Method GET | ConvertTo-Json -Depth 10 | ConvertFrom-Json | ||
try { | ||
$data = $response.value | ConvertTo-Json -Depth 10 | ConvertFrom-Json | ||
$directoryObjectList = @() | ||
$all = $All.IsPresent | ||
$increment = $topCount - $data.Count | ||
|
||
while ($response.'@odata.nextLink' -and (($all -and ($increment -lt 0)) -or $increment -gt 0)) { | ||
$params["Uri"] = $response.'@odata.nextLink' | ||
if ($increment -gt 0) { | ||
$topValue = [Math]::Min($increment, 999) | ||
$params["Uri"] = $params["Uri"].Replace('$top=999', "`$top=$topValue") | ||
$increment -= $topValue | ||
} | ||
$response = Invoke-GraphRequest -Headers $customHeaders -Uri $URI -Method $Method | ConvertTo-Json -Depth 10 | ConvertFrom-Json | ||
$data += $response.value | ConvertTo-Json -Depth 10 | ConvertFrom-Json | ||
} | ||
} catch {} | ||
|
||
foreach ($item in $data) { | ||
if ($null -ne $item) { | ||
# Determine the type based on @odata.type | ||
switch ($item.'@odata.type') { | ||
'#microsoft.graph.user' { | ||
$directoryObject = [Microsoft.Graph.PowerShell.Models.MicrosoftGraphUser]::new() | ||
} | ||
'#microsoft.graph.group' { | ||
$directoryObject = [Microsoft.Graph.PowerShell.Models.MicrosoftGraphGroup]::new() | ||
} | ||
default { | ||
Write-Warning "Unknown type: $($item.'@odata.type')" | ||
continue | ||
} | ||
} | ||
$item.PSObject.Properties | ForEach-Object { | ||
$propertyName = $_.Name | ||
$propertyValue = $_.Value | ||
$directoryObject | Add-Member -MemberType NoteProperty -Name $propertyName -Value $propertyValue -Force | ||
} | ||
$directoryObjectList += $directoryObject | ||
} | ||
} | ||
$directoryObjectList | ||
} | ||
} |
185 changes: 185 additions & 0 deletions
185
module/docs/entra-powershell-beta/Users/Get-EntraBetaUserSponsor.md
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change | ||||
---|---|---|---|---|---|---|
@@ -0,0 +1,185 @@ | ||||||
--- | ||||||
title: Get-EntraBetaUserSponsor | ||||||
description: This article provides details on the Get-EntraBetaUserSponsor command. | ||||||
|
||||||
ms.topic: reference | ||||||
ms.date: 02/10/2025 | ||||||
ms.author: eunicewaweru | ||||||
ms.reviewer: stevemutungi | ||||||
manager: CelesteDG | ||||||
author: msewaweru | ||||||
|
||||||
schema: 2.0.0 | ||||||
--- | ||||||
|
||||||
# Get-EntraBetaUserSponsor | ||||||
|
||||||
## Synopsis | ||||||
|
||||||
Retrieve a user's sponsors (users or groups). | ||||||
|
||||||
## Syntax | ||||||
|
||||||
```powershell | ||||||
Get-EntraBetaUserSponsor | ||||||
-UserId <String> | ||||||
[-All] | ||||||
[-Property <String[]>] | ||||||
[<CommonParameters>] | ||||||
``` | ||||||
|
||||||
### GetById | ||||||
|
||||||
```powershell | ||||||
Get-EntraBetaUserSponsor | ||||||
-UserId <String> | ||||||
-SponsorId <String> | ||||||
[-Property <String[]>] | ||||||
[<CommonParameters>] | ||||||
``` | ||||||
|
||||||
## Description | ||||||
|
||||||
The `Get-EntraBetaUserSponsor` cmdlet retrieve a user's sponsors (users or groups). The sponsor feature tracks who is responsible for each guest user by assigning a person or group, ensuring accountability. | ||||||
|
||||||
In delegated scenarios with work or school accounts, the signed-in user needs a supported Microsoft Entra role or a custom role with `microsoft.directory/users/sponsors/read permission`. The least privileged supported roles are: | ||||||
|
||||||
- Guest Inviter | ||||||
- Directory Readers | ||||||
- Directory Writers | ||||||
- User Administrator | ||||||
|
||||||
## Examples | ||||||
|
||||||
### Example 1: Get the user sponsors | ||||||
|
||||||
```powershell | ||||||
Connect-Entra -Scopes 'User.Read', 'User.Read.All' # User.Read.All is application-only permission (non-interactive login) | ||||||
Get-EntraBetaUserSponsor -UserId '[email protected]' | | ||||||
Select-Object Id, displayName, userPrincipalName, createdDateTime, accountEnabled, userType | | ||||||
Format-Table -AutoSize | ||||||
``` | ||||||
|
||||||
```Output | ||||||
id displayName userPrincipalName createdDateTime accountEnabled userType | ||||||
-- ----------- ----------------- --------------- -------------- -------- | ||||||
c0c97c58-1895-4910-b1bb-58f96db771df Adele Vance [email protected] 28/10/2024 09:50:43 True Member | ||||||
79984fce-9e33-497a-a5a2-b3c85e3fedcb Alex Wilber [email protected] 28/10/2024 09:50:46 True Member | ||||||
406e3c9f-7a2d-4ef0-b1d4-69ddbd2719bb Diego Siciliani [email protected] 28/10/2024 09:50:46 True Member | ||||||
``` | ||||||
|
||||||
This example shows how to list user sponsors. | ||||||
|
||||||
- The `-UserId` parameter specifies the User ID or User Principal Name. | ||||||
|
||||||
### Example 2: Get top one sponsor | ||||||
|
||||||
```powershell | ||||||
Connect-Entra -Scopes 'User.Read', 'User.Read.All' # User.Read.All is application-only permission (non-interactive login) | ||||||
Get-EntraBetaUserSponsor -UserId '[email protected]' -Top 1 | Select-Object Id, DisplayName, '@odata.type' | ||||||
``` | ||||||
|
||||||
```Output | ||||||
Id displayName @odata.type | ||||||
-- ----------- ----------- | ||||||
cccccccc-2222-3333-4444-dddddddddddd Contoso Group #microsoft.graph.group | ||||||
``` | ||||||
|
||||||
This example retrieves the top sponsor for the specified user. | ||||||
|
||||||
- The `-UserId` parameter specifies the User ID or User Principal Name. | ||||||
|
||||||
### Example 3: Retrieve the assigned sponsor for a specific user by their SponsorId | ||||||
|
||||||
```powershell | ||||||
Connect-Entra -Scopes 'User.Read', 'User.Read.All' # User.Read.All is application-only permission (non-interactive login) | ||||||
Get-EntraBetaUserSponsor -UserId '[email protected]' -SponsorId c0c97c58-1895-4910-b1bb-58f96db771df | Select-Object Id, DisplayName, '@odata.type' | ||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Suggested change
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Thank you, @alexandair for the catch! |
||||||
``` | ||||||
|
||||||
```Output | ||||||
Id displayName @odata.type | ||||||
-- ----------- ----------- | ||||||
cccccccc-2222-3333-4444-dddddddddddd Contoso Group #microsoft.graph.group | ||||||
``` | ||||||
|
||||||
This example retrieves the assigned sponsor for the specified user. | ||||||
|
||||||
- The `-UserId` parameter specifies the User ID or User Principal Name. | ||||||
- The `-SponsorId` parameter specifies the specific user's sponsor ID to retrieve. | ||||||
|
||||||
## Parameters | ||||||
|
||||||
### -All | ||||||
|
||||||
List all pages. | ||||||
|
||||||
```yaml | ||||||
Type: System.Management.Automation.SwitchParameter | ||||||
Parameter Sets: (All) | ||||||
Aliases: | ||||||
|
||||||
Required: False | ||||||
Position: Named | ||||||
Default value: False | ||||||
Accept pipeline input: False | ||||||
Accept wildcard characters: False | ||||||
``` | ||||||
|
||||||
### -UserId | ||||||
|
||||||
Specifies the ID (as a UserPrincipalName or UserId) of a user in Microsoft Entra ID. | ||||||
|
||||||
```yaml | ||||||
Type: System.String | ||||||
Parameter Sets: (All) | ||||||
|
||||||
Required: True | ||||||
Position: Named | ||||||
Default value: None | ||||||
Accept pipeline input: True (ByPropertyName, ByValue) | ||||||
Accept wildcard characters: False | ||||||
``` | ||||||
|
||||||
### -Top | ||||||
|
||||||
Specifies the maximum number of records to return. | ||||||
|
||||||
```yaml | ||||||
Type: System.Int32 | ||||||
Parameter Sets: (All) | ||||||
Aliases: Limit | ||||||
|
||||||
Required: False | ||||||
Position: Named | ||||||
Default value: None | ||||||
Accept pipeline input: True (ByPropertyName, ByValue) | ||||||
Accept wildcard characters: False | ||||||
``` | ||||||
|
||||||
### -Property | ||||||
|
||||||
Specifies properties to be returned. | ||||||
|
||||||
```yaml | ||||||
Type: System.String[] | ||||||
Parameter Sets: (All) | ||||||
DButoyez marked this conversation as resolved.
Show resolved
Hide resolved
|
||||||
Aliases: Select | ||||||
|
||||||
Required: False | ||||||
Position: Named | ||||||
Default value: None | ||||||
Accept pipeline input: False | ||||||
Accept wildcard characters: False | ||||||
``` | ||||||
|
||||||
### CommonParameters | ||||||
|
||||||
This cmdlet supports the common parameters: `-Debug`, `-ErrorAction`, `-ErrorVariable`, `-InformationAction`, `-InformationVariable`, `-OutVariable`, `-OutBuffer`, `-PipelineVariable`, `-Verbose`, `-WarningAction`, and `-WarningVariable`. For more information, see [about_CommonParameters](https://go.microsoft.com/fwlink/?LinkID=113216). | ||||||
|
||||||
## Inputs | ||||||
|
||||||
## Outputs | ||||||
|
||||||
## Notes | ||||||
|
||||||
## Related Links |
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.