Mailbox Import-Export Graph APIs Leave No Audit Trail

Use the Import-Export Graph API to Copy Data from Mailboxes Without a Trace

A recent LinkedIn post by a security practitioner set some alarm bells ringing when it disclosed that the Graph Mailbox Import-Export APIs processed mailbox content without creating audit events to track activity. Given that a) any operation that can exfiltrate mailbox data could be a highly prized tool for attackers and b) the extensive auditing capabilities built into Microsoft 365, this oversight is more than surprising.

What’s poignant about the situation is that Microsoft released the Mailbox Import-Export Graph APIs as part of their campaign to eliminate Exchange Web Services (EWS). EWS is deemed to be insecure and was used to exfiltrate mailbox data from many sensitive executive mailboxes in the Midnight Blizzard attack on Microsoft’s own tenant in March 2024.

Since then, Microsoft has been on a campaign to eradicate EWS from Microsoft 365 as quickly as practicable. The deadline for all apps to stop using EWS is October 2026, and Microsoft plans to eliminate EWS from first-party apps by October 2025, with recent moves to lay the path for Exchange Online and Teams to stop using EWS to share free-busy information and other data.

To be fair to Microsoft, the Mailbox Import-Export Graph API is in preview and beta software usually has a few holes to fill before it can become generally available. On the other hand, Microsoft launched the API in January 2025 and you’d imagine that someone in the development team would have noticed by now. The good news is that Microsoft has acknowledged the issue. I don’t imagine that it will take them long to begin generating audit events for import and export activities.

For an independent take on using the Mailbox Import-Export Graph API, I recommend reading the articles published by MVP Glen Scales.

Testing Auditing of Permanent Removals

Another step in the EWS removal process came with the launch of APIs to permanently remove mailbox items (including calendar items, contacts, and events). Given the issue reported above, I wanted to check if Exchange Online generated audit events for the permanent removal APIs. It’s not inconceivable that an attacker would seek to remove some items from a mailbox, and so much the better if they can do it without detection.

I processed some permanent deletions for mailbox objects and then ran an audit search for hard deletions (which is what these events are).

[array]$Records = Search-UnifiedAuditLog -StartDate '29-May-2025 10:00' -EndDate (Get-Date) -Formatted -SessionCommand ReturnLargeSet -ResultSize 5000 -Operations 'HardDelete'

Audit events for the permanent deletions duly turned up.

Permanent Removals of Calendar Events

I then processed a permanent deletion of a calendar event by finding some events in my own calendar, selecting one, and deleting it:

[array]$Events = Get-MgUserCalendarView -UserId $userId -Startdatetime "2025-01-01T19:00:00-08:00" -Enddatetime "2025-02-20T19:00:00-08:00"
$Event = $Events[1]
$Uri = $("https://graph.microsoft.com/v1.0/users/{0}/Events/{1}/permanentdelete" -f $UserId, $Event.Id)
Invoke-MgGraphRequest -Uri $Uri -Method Post

Again, Exchange Online captured a hard delete audit event for the deletion (Figure 1)

Details of an audit event for a hard delete operation recording permanent removal of a calendar event.

Import-Export Graph API.
Figure 1: Details of an audit event for a hard delete operation recording permanent removal of a calendar event

Deleting different types of mailbox items permanently generates audit events. I expected this to be the case because these are not new APIs. Instead, Microsoft extended existing APIs to support permanent deletion, and the extension picked up the existing auditing mechanism.

Auditing is Critical

Some might consider the inclusion of auditing to be a small point when an API is in beta. It’s an arguable point, but the counter is that attackers don’t care if an API that can do a job for them is a beta or production API. All they worry about is the outcome, which could be a bunch of data noiselessly moved out of a tenant.

Of course, the tenant must be compromised beforehand, but evidence exists of cases where attackers penetrated a tenant and waited months before seizing an opportunity to do damage. A beta API that doesn’t generate audit records sounds like just the kind of tool attackers might like to use.


Need some assistance to write and manage PowerShell scripts for Microsoft 365? Get a copy of the Automating Microsoft 365 with PowerShell eBook, available standalone or as part of the Office 365 for IT Pros eBook bundle.

Leave a Reply

This site uses Akismet to reduce spam. Learn how your comment data is processed.