Skip to main content
Exchange Online · Microsoft Entra ID · PowerShell 7.6

Shared mailboxes whose account can still sign in

Which shared mailboxes have a user account that is still enabled for sign-in? Microsoft's guidance is to block sign-in for every shared mailbox account and keep it blocked.

Script

#Requires -Modules ExchangeOnlineManagement, Microsoft.Graph.Authentication, Microsoft.Graph.Users
# Shared mailboxes whose Entra ID user account is enabled for sign-in. Read-only.
param(
    [switch]$All
)

Connect-ExchangeOnline -ShowBanner:$false
Connect-MgGraph -Scopes 'User.Read.All' -NoWelcome

Get-EXOMailbox -ResultSize Unlimited -RecipientTypeDetails SharedMailbox |
    ForEach-Object {
        $user = Get-MgUser -UserId $_.ExternalDirectoryObjectId -Property 'id', 'accountEnabled', 'assignedLicenses', 'onPremisesSyncEnabled'
        [pscustomobject]@{
            Mailbox        = "$($_.PrimarySmtpAddress)"
            DisplayName    = $_.DisplayName
            SignInEnabled  = $user.AccountEnabled -eq $true
            Licensed       = @($user.AssignedLicenses).Count -gt 0
            SyncedFromAD   = $user.OnPremisesSyncEnabled -eq $true
        }
    } |
    Where-Object { $All -or $_.SignInEnabled } |
    Sort-Object Mailbox

Checked automatically against Microsoft's published cmdlet reference. KBY hasn't run it in your tenant; run it in a test environment first.

Reading the output

  • Matches each shared mailbox to its Entra ID user through ExternalDirectoryObjectId, which is in Get-EXOMailbox's default (Minimum) property set, and reads accountEnabled from Microsoft Graph.
  • Pass -All to list every shared mailbox with its sign-in state, not only the enabled ones.
  • Accounts synced from on-premises Active Directory are marked SyncedFromAD; block sign-in for those by disabling the account in AD.
  • ExchangeOnlineManagement 3.10.0 and later require PowerShell 7.6 when run in PowerShell 7 (Windows PowerShell 5.1 is unaffected), per the module release notes.

Sources

The Microsoft reference page for every cmdlet the script calls, plus the API and product pages behind each permission and caveat.

All scripts