Generate Mailbox Usage Reports with Microsoft Graph PowerShell

Usage reports in Microsoft 365, such as the OneDrive, SharePoint and Mailbox usage reports, are a convenient way to get a quick overview of storage utilisation in your tenant. One problem which was raised on the Microsoft Q&A was that these reports cannot be configured to be sent to you automatically via email on a set period, specifically the Exchange Online mailbox usage report. 

The solution to this problem is to first generate the same reports using Microsoft Graph PowerShell. Once the report is generated, you then have the flexibility to either send them via email or drop them into a file share for later reading.

In this blog, I will show you how to use Microsoft Graph PowerShell to generate an Exchange Online mailbox usage reports from Microsoft 365.

Requirements

Exchange Online usage report

Below is a short script which will generate a mailbox usage report for all Exchange online mailboxes in your organisation. Specifically, this report will highlight the total amount of storage used for each mailbox in bytes, then it will convert that figure to Megabytes for readability. This is useful is migration scenarios or during licensing assessments. Although the period is not relevant in this report, to add confusion, you must still define the usage period even when it doesn’t impact the result.

For each of the below scripts, modify the $path variable to match the location to which you want to export the results.

Mailbox usage report

Connect-MgGraph -scopes Reports.Read.All
$path = "C:\temp\MailboxReport.csv"
Get-MgReportMailboxUsageDetail -Period D7 -OutFile $path
$report = import-csv $path
$report.Foreach({
    $_."storage used (Byte)" = '{0:N2} MB' -f ($_."storage used (Byte)" / 1MB)
})
$report | Export-CSV -Path $path -NoTypeInformation

All Microsoft Graph PowerShell usage report cmdlets

There are many other related Microsoft reports you can generate using PowerShell, some which do utilities the usage period and some which still don’t. Below is a list of all the available usage report cmdlets broken down into sections.

Print
Get-MgReportDailyPrintUsageByPrinter
Get-MgReportDailyPrintUsageByPrinterCount
Get-MgReportDailyPrintUsageByUser
Get-MgReportDailyPrintUsageByUserCount
Get-MgReportMonthlyPrintUsageByPrinter
Get-MgReportMonthlyPrintUsageByPrinterCount
Get-MgReportMonthlyPrintUsageByUser
Get-MgReportMonthlyPrintUsageByUserCount

Mail
Get-MgReportEmailAppUsageAppUserCount
Get-MgReportEmailAppUsageUserCount
Get-MgReportEmailAppUsageUserDetail
Get-MgReportEmailAppUsageVersionUserCount
Get-MgReportMailboxUsageDetail
Get-MgReportMailboxUsageMailboxCount
Get-MgReportMailboxUsageQuotaStatusMailboxCount
Get-MgReportMailboxUsageStorage

OneDrive
Get-MgReportOneDriveUsageAccountCount
Get-MgReportOneDriveUsageAccountDetail
Get-MgReportOneDriveUsageFileCount
Get-MgReportOneDriveUsageStorage

SharePoint
Get-MgReportSharePointSiteUsageDetail
Get-MgReportSharePointSiteUsageFileCount
Get-MgReportSharePointSiteUsagePage
Get-MgReportSharePointSiteUsageSiteCount
Get-MgReportSharePointSiteUsageStorage

Teams device
Get-MgReportSkypeForBusinessDeviceUsageDistributionUserCount
Get-MgReportSkypeForBusinessDeviceUsageUserCount
Get-MgReportSkypeForBusinessDeviceUsageUserDetail
Get-MgReportTeamDeviceUsageDistributionUserCount
Get-MgReportTeamDeviceUsageUserCount
Get-MgReportTeamDeviceUsageUserDetail

Yammer
Get-MgReportYammerDeviceUsageDistributionUserCount
Get-MgReportYammerDeviceUsageUserCount

Report periods

The supported report periods for Microsoft Graph PowerShell match that of what is supported through the Microsoft 365 admin center. Below are the supported usage periods in days:

  • D7
  • D30
  • D90
  • D180

Automating the reports via email

Each report can be automated to be sent via email to a user’s mailbox, group or shared mailbox. To achieve this, the emails can be sent using Microsoft Graph and automated using Microsoft Graph PowerShell. Here is an example of the code I use to send mail using Microsoft Graph PowerShell:

(This Send-MgUserMail cmdlet is found within the Microsoft.Graph.Users.Actions module and requires the mail.send permission to be consented to).

$Attachment = %filepath%
$MailAttachement = [Convert]::ToBase64String([IO.File]::ReadAllBytes($Attachment))

$body = @{
	message = @{
		subject = "Org Mailbox Report"
		body = @{
			contentType = "Text"
			content = "Please see the attached"
		}
		toRecipients = @(
			@{
				emailAddress = @{
					address = "%TO ADDRESS%"
				}
			}
		)
        attachments = @(
			@{
				"@odata.type" = "#microsoft.graph.fileAttachment"
				name = "$Attachment"
				contentType = "text/plain"
				contentBytes = $MailAttachement
			}
        )
	}
	saveToSentItems = "false"
}

Send-MgUserMail -UserId $from -BodyParameter $body

This process can be automated using Azure Automation, to ensure it runs securely and not from a physical or virtual server. This process I have covered in detail in my blog How to Run Microsoft Graph PowerShell Scripts With Azure Automation.

Daniel Bradley

My name is Daniel Bradley and I work with Microsoft 365 and Azure as an Engineer and Consultant. I enjoy writing technical content for you and engaging with the community. All opinions are my own.

This Post Has One Comment

  1. Caz

    Great Post, thank you.

    Typo:

    This is useful is migration scenarios or during licensing assessments.

Leave a Reply