Simple command turned crazy. I ended up coming up with this due to the fact we have duplicate display names and needed to update for Exchange Online to get mailbox sizes.

Get-Mailbox -ResultSize Unlimited | select @{ Name = 'Identity';  Expression = {$_.primarysmtpaddress}} | Get-MailboxStatistics | Select DisplayName, @{name=”TotalItemSize”;expression={[math]::Round($($_.totalitemsize.Value.ToString().replace(",","").split("(")[1].split(" bytes")[0])/1GB,2)}} | Where {$_.TotalItemSize -gt 45} | ft -auto

Breakdown of the code

Get-Mailbox gets all the mailboxes available, there’s no search filter on this one.

Get-Mailbox -ResultSize Unlimited

The select statement is used for doing a select expression where we can transform the Identity parameter that is being used as pipeline input for the Get-MailboxStatistics. I did this mainly because we have duplicate display names and differing email addresses in this specific tenant.

| select @{ Name = 'Identity';  Expression = {$_.primarysmtpaddress}}

Get-MailboxStatistics accept pipeline input of the default variable Identity. By doing the select statement above, we’re now using -Identity via the pipeline using the primary SMTP email address. This command outputs the data about a mailbox.

| Get-MailboxStatistics

This next select statement gives us the TotalItemSize formatted for use with comparison.

| Select DisplayName, @{name=”TotalItemSize”;expression={[math]::Round($($_.totalitemsize.Value.ToString().replace(",","").split("(")[1].split(" bytes")[0])/1GB,2)}}

This part of the select statement is broken down as follows:
The first part is the beginning of a select expression, the { is the start of the expression that will now become TotalItemSize.

@{name="TotalItemSize";expression={}}

Next up, we have the [math] function, we use this because by doing the simple math, we’d have a large amount of decimal places, so we round it.

[math]::Round()

Inside the () for the Round, we have this expression

$_.totalitemsize.Value.ToString().replace(",","").split("(")[1].split(" bytes")[0])/1GB

The TotalItemSize is modified to become a string

$_.totalitemsize.Value.ToString()

then we replace the commas in the string

.replace(",","")

split it at the first ( and grab the second part of the array

.split("(")[1]

then split again at bytes and grab the first part of that array

.split(" bytes")[0]

Finally we finish the Round() statement with a ,2 which gives us 2 decimal places rounded.

The next pipeline sets the where-object and we’re only concerned about mailboxes over 45 GB in this example. You can change this to whatever you’d like to filter based on.

| Where {$_.TotalItemSize -gt 45}