Entra / Microsoft 365 · Compliance & audit
Find Copilot audit records
Find and report unified audit log records generated for Copilot for Microsoft 365 interactions, excluding mobile devices.
Connect & set up
Run these once per session. All scopes are read-only unless the script makes changes.
Connect-ExchangeOnline -SkipLoadingCmdletHelp
Run it
The main script. Copy it, or download the .ps1 and run it from your console.
$ModulesLoaded = Get-Module | Select-Object -ExpandProperty NameIf ("ExchangeOnlineManagement" -notin $ModulesLoaded) {Write-Host "Connecting to Exchange Online..."Connect-ExchangeOnline -SkipLoadingCmdletHelp}Write-Host "Searching for Copilot audit records..."[array]$Records = Search-UnifiedAuditLog -StartDate (Get-Date).Adddays(-90) -EndDate (Get-Date).AddDays(1) -Formatted `-ResultSize 5000 -SessionCommand ReturnLargeSet -Operations CopilotInteractionIf (!($Records)) {Write-Host "No Copilot audit records found - exiting"Break} Else {# Remove any duplicate records and make sure that everything is sorted in date order$Records = $Records | Sort-Object Identity -Unique$Records = $Records | Sort-Object {$_.CreationDate -as [datetime]}Write-Host ("{0} Copilot audit records found. Now analyzing the content" -f $Records.count)}$Report = [System.Collections.Generic.List[Object]]::new()ForEach ($Rec in $Records) {$AuditData = $Rec.AuditData | ConvertFrom-Json$CopilotApp = 'Copilot for Microsoft 365'; $Context = $null; $CopilotLocation = $nullSwitch ($Auditdata.copiloteventdata.contexts.type) {"xlsx" {$CopilotApp = "Excel"}"docx" {$CopilotApp = "Word"}"pptx" {$CopilotApp = "PowerPoint"}"TeamsMeeting" {$CopilotApp = "Teams"$CopilotLocation = "Teams meeting"}"StreamVideo" {$CopilotApp = "Stream"$CopilotLocation = "Stream video player"}}If ($Auditdata.copiloteventdata.contexts.id -like "*https://teams.microsoft.com/*") {$CopilotApp = "Teams"} ElseIf ($AuditData.CopiloteventData.AppHost -eq "bizchat" -or $AuditData.CopiloteventData.AppHost -eq "Office") {$CopilotApp = "Copilot for Microsoft 365 Chat"}If ($Auditdata.CopilotEventData.contexts.id) {$Context = $Auditdata.CopilotEventData.contexts.id} ElseIf ($Auditdata.CopilotEventData.threadid) {$Context = $Auditdata.CopilotEventData.threadid# $CopilotApp = "Teams"}If ($Auditdata.copiloteventdata.contexts.id -like "*/sites/*") {$CopilotLocation = "SharePoint Online"} ElseIf ($Auditdata.copiloteventdata.contexts.id -like "*https://teams.microsoft.com/*") {$CopilotLocation = "Teams"If ($Auditdata.copiloteventdata.contexts.id -like "*ctx=channel*") {$CopilotLocation = "Teams Channel"} Else {$CopilotLocation = "Teams Chat"}} ElseIf ($Auditdata.copiloteventdata.contexts.id -like "*/personal/*") {$CopilotLocation = "OneDrive for Business"}# Make sure that we report the resources used by Copilot and the action (like read) used to access the resource[array]$AccessedResources = $AuditData.copiloteventdata.accessedResources.name | Sort-Object -Unique[string]$AccessedResources = $AccessedResources -join ", "[array]$AccessedResourceLocations = $AuditData.copiloteventdata.accessedResources.id | Sort-Object -Unique[string]$AccessedResourceLocations = $AccessedResourceLocations -join ", "[array]$AccessedResourceActions = $AuditData.copiloteventdata.accessedResources.action | Sort-Object -Unique[string]$AccessedResourceActions = $AccessedResourceActions -join ", "$ReportLine = [PSCustomObject][Ordered]@{TimeStamp = (Get-Date $Rec.CreationDate -format "dd-MMM-yyyy HH:mm:ss")User = $Rec.UserIdsApp = $CopilotAppLocation = $CopilotLocation'App context' = $Context'Accessed Resources' = $AccessedResources'Accessed Resource Locations' = $AccessedResourceLocationsAction = $AccessedResourceActions}$Report.Add($ReportLine)}$Report | Out-GridView -Title "Copilot for Microsoft 365 Audit Records"Write-Host ""Write-Host ("{0} Copilot audit records processed" -f $Records.count)Write-Host ""Write-Host "Summary of Copilot audit records by app"Write-Host "----------------------------------------"$Report | Group-Object App -NoElement | Sort-Object Count -Descending | Format-Table Name, count
Attribution
Author
Office365itpros