M365Microsoft 365PurviewPurviewTeamsTeams

Teams chats without an Exchange Online licence: why they fall outside eDiscovery and retention

10 October 2026  ·  6 min leestijd  ·  Kevin Oosterlaken

Mail never moved to the cloud. It runs on Exchange on-premises, so when the E5 licences went in, someone switched off the Exchange Online service plan. It felt like good housekeeping: nobody gets a second, empty mailbox, and nobody's mail ends up in the wrong place.

Two years later, legal asks for the Teams chats of an employee who left. eDiscovery comes back empty. Not because the chats were deleted. Because they were never kept.

Where Teams keeps its compliance copy

Teams stores its messages in an Azure-powered chat service. That's what the app shows you. But eDiscovery, holds and retention never look there. They work on a compliance copy in Exchange Online: chats land in a hidden folder in the mailbox of every participant, and channel messages in the mailbox of the team's Microsoft 365 group. Microsoft is blunt about the difference:

Messages visible in the Teams app are not an accurate reflection of whether they're retained or permanently deleted for compliance requirements.

For users whose mailbox lives on-premises, Microsoft creates a separate cloud-based storage area in Exchange Online, just for their Teams chats. That's the "shadow mailbox" people talk about. And it comes with a condition.

The licence condition nobody reads

From Microsoft's documentation on Teams and Exchange:

Switch off the Exchange Online service plan in the licence, never switch it on, and that storage isn't there. For cloud-only users the story is simpler: their chats go into their own Exchange Online mailbox, so no Exchange Online plan means no mailbox to put them in. Either way, that user's chats sit outside eDiscovery, holds and retention.

The cruel part is that switching the plan off is often the responsible choice. Microsoft's own docs warn that in an organization without an Exchange hybrid deployment, assigning that licence to someone whose mailbox is on-premises, without syncing the on-premises Exchange schema, risks creating a duplicate cloud mailbox. So admins switch it off to avoid one mess and walk straight into another.

A few nuances before you panic, or relax:

It's not only Teams

The mailbox is Microsoft 365's filing cabinet for more than mail. According to the eDiscovery documentation, Copilot prompts and responses, To Do tasks, Microsoft Forms and private Viva Engage messages are also stored in, or associated with, Exchange Online mailboxes. The same logic applies: no mailbox, no compliance copy.

Find the users it already applies to

This read-only script reads licence data from Microsoft Graph and lists every user who has the Teams service plan but no Exchange Online Plan 1 or Plan 2. It changes nothing; it only reads.

#Requires -Modules Microsoft.Graph.Authentication, Microsoft.Graph.Users, Microsoft.Graph.Identity.DirectoryManagement

<#
.SYNOPSIS
    Lists users who have Teams but no Exchange Online Plan 1 or Plan 2.
.DESCRIPTION
    Read-only. Teams chats are kept for compliance in Exchange Online. Users with
    the Teams service plan enabled but no Exchange Online Plan 1 or Plan 2
    enabled have no place for that copy, so their chats fall outside
    eDiscovery, holds and retention.
.NOTES
    Modules : Microsoft.Graph.Authentication, Microsoft.Graph.Users,
              Microsoft.Graph.Identity.DirectoryManagement
    Scopes  : User.Read.All, LicenseAssignment.Read.All (delegated, read-only)
    Plan IDs: from "Product names and service plan identifiers for licensing"
              on Microsoft Learn. Checks TEAMS1, the Teams plan in the
              Microsoft 365 and Office 365 suites; add other Teams plan IDs if
              you use standalone or government SKUs.
    Licence data only: it can't see where a hybrid user's mailbox lives.
#>
$ErrorActionPreference = 'Stop'
Connect-MgGraph -Scopes 'User.Read.All', 'LicenseAssignment.Read.All' -NoWelcome

$teamsPlan = '57ff2da0-773e-42df-b2af-ffb7a2317929'      # TEAMS1
$exoPlans  = @{
    '9aaf7827-d63c-4b61-89c3-182f06f82e5c' = 'Plan 1'     # EXCHANGE_S_STANDARD
    'efb87545-963c-4e0d-99df-69c6916d9eb0' = 'Plan 2'     # EXCHANGE_S_ENTERPRISE
    '4a82b400-a79f-41a4-b4e2-e94f5787b113' = 'Kiosk'      # EXCHANGE_S_DESKLESS
}

# 1. Which service plans each licence (SKU) in the tenant contains
$skuPlans = @{}
foreach ($sku in Get-MgSubscribedSku -All) {
    $skuPlans["$($sku.SkuId)"] = @($sku.ServicePlans | ForEach-Object { "$($_.ServicePlanId)" })
}

# 2. Per user: enabled plans = the SKU's plans minus the disabled ones.
#    assignedLicenses includes group-based licences.
$report = foreach ($u in Get-MgUser -All -Property Id, UserPrincipalName, AccountEnabled, AssignedLicenses) {
    $enabled = foreach ($lic in $u.AssignedLicenses) {
        $disabled = @($lic.DisabledPlans | ForEach-Object { "$_" })
        $skuPlans["$($lic.SkuId)"] | Where-Object { $_ -notin $disabled }
    }
    if ($teamsPlan -notin $enabled) { continue }      # no Teams, no Teams chats

    $exo = @($exoPlans.Keys | Where-Object { $_ -in $enabled } | ForEach-Object { $exoPlans[$_] })
    if ($exo -contains 'Plan 1' -or $exo -contains 'Plan 2') { continue }

    [pscustomobject]@{
        User     = $u.UserPrincipalName
        Enabled  = $u.AccountEnabled
        Exchange = $(if ($exo) { $exo -join ', ' } else { 'none' })
        Note     = $(if ($exo) { 'Kiosk mailbox: fine in the cloud, below the Plan 1 minimum if the mailbox is on-premises' }
                     else      { 'No Exchange Online plan: chats not kept for compliance' })
    }
}

$report | Sort-Object Exchange, User | Format-Table -AutoSize -Wrap
'{0} Teams users without Exchange Online Plan 1 or Plan 2.' -f @($report).Count

Reading the result. Every none is a user whose Teams chats aren't kept for compliance, and Enabled = False rows are the leavers you'll be asked about first. A Kiosk row is usually fine for a cloud mailbox, but below the documented minimum if that mailbox is on-premises. And for hybrid users, look one step further than this script can: according to Microsoft's on-premises article, holds and retention on their chats need Plan 2, not Plan 1.

Switching off Exchange Online in a licence looks like housekeeping. For Teams, it's a compliance decision. Make it on purpose, and find out who it already applies to before someone from legal does.

Sources: Search for Teams chat data for on-premises users, How Exchange and Microsoft Teams interact, Learn about retention for Microsoft Teams, Finding content in mailboxes in eDiscovery, Product names and service plan identifiers for licensing, Place a mailbox on litigation hold.

← Alle posts Contact