Get in touch with us!

Retrieve and analyze Office 365 Usage Data with PowerShell and Microsoft Graph API

Why usage data is important | The move to Office 365 is not just about moving a bunch of data to someone else’s datacenter. It is a more modern way of working which provides fantastic opportunities around collaboration both internally and externally, spreading  information with audio and video, smart tools built upon machine learning and AI, intelligent security solutions that talks to each other and a lot more.
To buy an Office 365 license for a user means that he will get access to much more than just email and intranet. To drive adoption and to make sure that the users learn to get the most out of the new opportunities, you have to measure how the different services are used and how much. This is where usage data comes in.

Microsoft has a number of measure points for each service which can be accessed through the usage reports in the Office 365/Microsoft 365 admin portal. Microsoft stores 180 days’ worth of data. You can also access this data in Power BI with Microsoft 365 Usage Analytics (former Office 365 Adoption Content Pack).

These two tools work well if you want to get started with adoption and get an overview on the current situation and what effects user training for a specific service might have for example. If you want to take it to the next level there are endless possibilities for customization if you read the usage data and manage it thought scripts and apps.

Retrieve Office 365 usage data with Microsoft Graph

In the Office 365/Microsoft 365 admin portal you can export the usage data in CSV format. The CSV data that you get in the portal is the same as you get if you query Microsoft Graph (Microsoft is probably using Graph as well). Because I live and brethe PowerShell I chose to work with Microsoft Graph through a PowerShell script but it’s also possible t9 do this from a .NET application or anything that can talk with a REST API.

With a couple of smart tricks in PowerShell we can convert the CSV data that Graph returns to regular PowerShell objects. After that we can work with the objects just as we always do in PowerShell, like Format-Table, Format-List, Out-GridView or why not store the data in a SQL database and use Power BI to analyze it.

Register an app for Microsoft Graph in Azure AD

For our PowerShell script to be able to connect to Graph and retrieve the data we must first register an app in Azure AD and grant it permissions to read user data. We will do this in the Azure Portal.

Go to Azure Active Directory and App registrations.

Create a new app and fill in the form like this.

Note the application ID. We will use this in the script.

Open the properties of the new app and click on Keys. Create a new key by enter a Description and then click Save.

Note the key that will show up under Value (you can only see the key this one time so make sure you save it somewhere).

Click on Required permissions and then on Add.

Chose Microsoft Graph under API.

Chose Read all usage reports under Select permissions and then click Save.

Grant the permissions that we added by clicking Grant Permissions. This must be done by an administrator so if you don’t have administrative permissions in Azure AD you have to ask an administrator to grant the permissions instead.

PowerShell function that connects to Microsoft Graph

This function is a general Graph connect function and it will connect to Graph and then call a URL that will return the answer.

function Get-GraphApi {
 param (




 # Graph API URLs.
 $LoginUrl = ""
 $RresourceUrl = ""
 # Compose REST request.
 $Body = @{ grant_type = "client_credentials"; resource = $RresourceUrl; client_id = $ClientID; client_secret = $ClientSecret }
 $OAuth = Invoke-RestMethod -Method Post -Uri $LoginUrl/$TenantName/oauth2/token?api-version=1.0 -Body $Body
 # Check if authentication is successfull.
 if ($OAuth.access_token -eq $null)
 Write-Error "No Access Token"
 # Perform REST call.
 $HeaderParams = @{ 'Authorization' = "$($OAuth.token_type) $($OAuth.access_token)" }
 $Result = (Invoke-WebRequest -UseBasicParsing -Headers $HeaderParams -Uri $Url)

# Return result.

We will call this function from our Get-UsageReportData function below. Get-UsagReportData is also the function that will handle the raw data that Graph returns and then filter out the CSV content and convert it to PowerShell objects. Note the trick we are using to split “\?\?\?” to remove the raw data that comes before the CSV part in the response from Microsoft Graph.

function Get-UsageReportData {
 param (
 [parameter(Mandatory = $true)]

[parameter(Mandatory = $true)]

[parameter(Mandatory = $true)]
try {
 # Call Microsoft Graph and extract CSV content and convert data to PowerShell objects.
 ((Get-GraphApi -ClientID $ClientID -ClientSecret $ClientSecret -TenantName $TenantName -Url $GraphUrl).RawContent -split "\?\?\?")[1] | ConvertFrom-Csv
 catch {

With these two functions in place it is simple to retreive usage data in the following way.

$ClientID = "e05e2a69-26b0-4496-bc47-befd55b83f16" # You registered apps App ID.
$ClientSecret = "oo87Z52Ckr7Q0AzLKqtFH567Dne4FQvWeVs2rNYG/Pw=" # Your registered apps key.
$TenantName = "" # Your tenant name.
$GraphUrl = "'D7')" # The Graph URL to retrieve data.

$UsageData = Get-UsageReportData -ClientID $ClientID -ClientSecret $ClientSecret -TenantName $TenantName -GraphUrl $GraphUrl

Example output:

Report Refresh Date : 2018-09-21
User Principal Name :
Last Activity Date : 2018-09-21
Is Deleted : False
Deleted Date :
Team Chat Message Count : 4
Private Chat Message Count : 333
Call Count : 3
Meeting Count : 1
Has Other Action : Yes
Report Period : 7

In this case we are retreiving the usage data of all Teams users from the last month. Additional information about this exact Graph URL can be found here:


All avaiable usage data reports that can be retreived can be found in the menu on this page.


Here are some examples of reports that you can get data from.

Data URL
User Outlook activity'{period_value}’)
User OneDrive activity'{period_value}’)
User SharePoint activity'{period_value}’)

How Altitude 365 use this

Even though the built-in reports are powerful we can do a lot more when we retreive the usage data and manage it ourselves. Here at Altitude 365 we use the usage data together with Power BI to help our customers with adoption, license optimization, clean-up, security and automatic advisory that would not have been possible without using Microsoft Graph. The customer get amazing intights in how there organization uses Office 365.

If you are interested in building solutions against Microsoft Graph or if you need assistance with adoption, license optimization, and more, Altitude 365 can help you. Contact us if you want to learn more!

1 Comment

  1. xmzhou


    Global Admin followed all steps above creating id and key for me. when I accessed to $GraphUrl = “’D7′)”, I got System.Net.WebException
    The remote server returned an error: (403) Forbidden. anything I missed?

    Thanks in advance!


Submit a Comment

Your email address will not be published. Required fields are marked *

Starkare tillsammans

Bolag inom både publik och offentlig sektor efterfrågar en alltmer kostnadseffektiv, platsoberoende och säker digital arbetsplats. Därför går nu Altitude 365 och Uclarity samman och bildar ett gemensamt specialistbolag.
Fortsätt på Altitude 365Kolla in Exobe

Altitude 365 + Uclarity – Årets Modern Work Partner!

Vinnaren är ett bra exempel på hur en “Born in the Cloud” ständigt förbättrar sitt erbjudande, arbetar nära och proaktivt med Microsoft för att hjälpa kunderna på deras digitaliseringsresa. Plus att vi på Microsoft verkligen ser fram mot den nya bolags-konstellationen (Altitude 365 + Uclarity) för ett “Starkare Tillsammans”.

Uclarity och Altitude 365 - Starkare tillsammans

Uclarity är specialister på digitala möten, telefoni, kontaktcenter och digitalt arbetssätt. Altitude 365 är specialister på säkerhet, mobilitet och hur bolag kan optimera resan till Microsoft365. Nu gör vi gemensam sak och bildar bolag tillsammans.

– Pandemin har tydliggjort behoven av en modern digital arbetsplats och vi har diskuterat ett samgående med Altitude 365 under en längre tid. Våra kunder har behov av specialistkompetens och tillsammans blir vi en ledande specialist inom Digital Workplace-området, säger Niklas Olsson Hellström, VD Uclarity AB.

Tommy Clark, Partner, Altitude 365, kommenterar:
– Inget bolag köper det andra utan båda bolagen får lika stora delar i det nya bolaget. Vår ledstjärna är att vi blir starkare tillsammans och att vi kan hjälpa våra kunder under hela deras resa.
Målet med sammanslagningen är att kunna hjälpa kunder med både teknik och effektiva arbetssätt.

– Det är då våra kunder får önskad effekt av sin investering i den digitala arbetsplatsen, säger Niklas Olsson Hellström.

Båda bolagen har svenska och internationella kunder från både privat och offentlig sektor. Sammanslagningen resulterar i en organisation på 50+ anställda baserade i Stockholm, Örebro och Göteborg.

För frågor, vänligen kontakta;
Tommy Clarke, Partner, Altitude 365 AB, 0703-593854,
Niklas Olsson Hellström, VD, Uclarity AB, 0734-198016,

Fortsätt på Altitude 365Kolla in Exobe