Fetch External Users in Microsoft Teams Using Graph PowerShell

Microsoft Teams allows seamless collaboration across organizations by enabling external users (guests) to join your Teams. However, as an administrator, you may need to monitor and report on these external users to ensure secure collaboration. This article provides a Graph PowerShell script to query all Teams in your tenant and list the external (guest) users along with their details such as Team Name, Member Name, and Team Type.
This script simplifies identifying external users and ensures compliance with your organization's security policies.

The Script


# Connect to Microsoft Graph
Connect-MgGraph -Scopes "Group.Read.All User.Read.All"

# Initialize the output array
$ExternalUsers = @()

Write-Host "Fetching all Teams..." -ForegroundColor Cyan

# Fetch all Teams
$Teams = Get-MgGroup -Filter "resourceProvisioningOptions/Any(x:x eq 'Team')" -All -Property Id, DisplayName, GroupTypes

if ($Teams.Count -eq 0) {
    Write-Host "No Teams found. Verify if there are any Teams in your tenant." -ForegroundColor Red
    return
}

Write-Host "Total Teams found: $($Teams.Count)" -ForegroundColor Green

# Iterate through each Team
foreach ($Team in $Teams) {
    $TeamId = $Team.Id
    $TeamName = $Team.DisplayName
    $TeamType = if ($Team.GroupTypes -contains "Unified") { "Public" } else { "Private" }
    
    Write-Host "Processing Team: $TeamName ($TeamType)" -ForegroundColor Yellow

    # Fetch Members of the Team
    $Members = Get-MgGroupMember -GroupId $TeamId -All

    if ($Members.Count -eq 0) {
        Write-Host "No members found in Team: $TeamName" -ForegroundColor DarkYellow
        continue
    }

    # Iterate through members and fetch details using Get-MgUser
    foreach ($Member in $Members) {
        try {
            # Fetch user details using Get-MgUser
            $UserDetails = Get-MgUser -UserId $Member.Id -Property DisplayName, UserPrincipalName, UserType

            # Check if the user is a guest (external)
            if ($UserDetails.UserType -eq "Guest") {
                # Extract External Domain Name
                $ExternalDomain = $UserDetails.UserPrincipalName.Split("@")[-1]

                # Add to Output Array
                $ExternalUsers += [PSCustomObject]@{
                    "Team Name"      = $TeamName
                    "Member Name"    = $UserDetails.DisplayName
                    "Team Type"      = $TeamType
                    "External Domain" = $ExternalDomain
                }
            }
        } catch {
            Write-Host "Failed to fetch details for member ID: $($Member.Id)" -ForegroundColor Red
        }
    }
}

# Output the results in tabular format
if ($ExternalUsers.Count -gt 0) {
    $ExternalUsers | Format-Table -AutoSize
    $ExternalUsers | Export-Csv -Path "ExternalUsersInTeams.csv" -NoTypeInformation -Encoding UTF8
    Write-Host "Results exported to 'ExternalUsersInTeams.csv'" -ForegroundColor Green
} else {
    Write-Host "No external users (guests) found in any Teams." -ForegroundColor Red
}
                            

How the Script Works

  1. Connect to Graph API:
    The script starts by authenticating to Microsoft Graph with the required permissions (Group.Read.All and User.Read.All).
  2. Fetch Teams:
    It queries all Teams in the tenant using the Get-MgGroup cmdlet with a filter on resourceProvisioningOptions.
  3. Retrieve Members:
    For each Team, the Get-MgGroupMember cmdlet fetches all member IDs.
  4. Fetch Member Details:
    The Get-MgUser cmdlet is used to retrieve detailed properties (e.g., UserPrincipalName, UserType) for each member.
  5. Identify Guests:
    External users are identified by the UserType property being “Guest”.
  6. Compile Results:
    The script collects guest user information, including their associated Team, name, type.
  7. Export Results:
    Finally, the results are displayed in a table and exported to a CSV file for further analysis.

Further Enhancements

  1. Pagination Support:
    If the tenant has a large number of Teams or members, add pagination logic to handle API limits.
  2. Filter by Domain:
    Modify the script to include a domain filter for specific external organizations.
  3. Detailed Reports:
    Enhance the report by including additional fields such as the user's role (e.g., owner or member) or when they were added to the Team.
  4. Automation:
    Schedule the script to run regularly and send reports via email.

Possible Errors and Solutions

Error Cause Solution
Insufficient privileges to complete the operation Missing permissions in Graph API. Ensure the signed-in account has the following delegated permissions: Group.Read.All, User.Read.All
No external users found. Verify that Teams have external users. Verify that Guest access is enabled in Teams settings Enable guest access in the Teams admin center.
API Throttling Too many requests sent to Microsoft Graph in a short time. Exceeding Graph API rate limits. Implement delays between API calls or query users in batches.

Conclusion

This Graph PowerShell script provides a powerful way to monitor and report on external (guest) users in Microsoft Teams. By leveraging Microsoft Graph, administrators can ensure secure collaboration across Teams and maintain compliance with organizational policies. With further enhancements, this script can be tailored to meet specific reporting needs, such as domain filtering or automated alerts.


Suggested Reading

© m365corner.com. All Rights Reserved. Design by HTML Codex