Build seamless automations to boost productivity with Microsoft Graph, Azure Event Hubs and Functions

Every day millions of people spend their precious time in productivity tools. What if you use data and intelligence behind the Microsoft applications (Microsoft Teams, Outlook, and many other Office apps) to build seemsless automations and custom apps to boost productivity? In this post, we’ll build a seamsless onboarding experience to new employees joining a company with the power of Microsoft Graph.

📝 What We’ll Cover

  • ✨ The power of Microsoft Graph
  • 🖇️ How do Microsoft Graph and Event Hubs work together?
  • ⚒️ Exercise: Setup Azure Event Hubs and Key Vault
  • 🪡 Exercise: Subscribe to users resource to receive change notifications by using Azure Functions
  • ♾️ Exercise: Create Onboarding Function
  • 🚀 Debug your onboarding experience
  • 📚 Resources

Following pre-requisites are recommended:

✨ The power of Microsoft Graph

Microsoft Graph is the gateway to data and intelligence in Microsoft 365 platform. Microsoft Graph exploses Rest APIs and client libraries to access data across Microsoft 365 core services such as Calendar, Teams, To Do, Outlook, People, Planner, OneDrive, OneNote and more.

Microsoft Graph Overview

You can build custom experiences by using Microsoft Graph such as automating the onboarding process for new employees. When new employees are created in the Azure Active Directory, they will be automatically added in the Onboarding team on Microsoft Teams.

Solutions Architecture

🖇️ How do Microsoft Graph and Event Hubs work together?

Microsoft Graph uses webhook mechanism to track changes in resources and deliver change notifications to the clients. As an example to the Microsoft Graph Change Notifications, you can receive change notifications when:

  • a new task is added in the to-do list
  • a user changes the presence status from busy to available
  • an event is deleted/cancelled from the calendar

If you’d like to track a large set of resources in a high frequency, you can use Azure Events Hubs instead of traditional webhooks to receive change notifications. Azure Event Hubs is a popular real-time events ingestion and distribution service built for scale.

Microsoft Graph Change Notifications can be also received by using Azure Event Grid that is currently available for Microsoft Partners. Please review the documentation for more information: Partner Events overview for customers – Azure Event Grid

⚒️ Exercise: Setup Azure Event Hubs and Key Vault

To get Microsoft Graph Change Notifications delivered to Azure Event Hubs, we’ll have to setup Azure Event Hubs and Azure Key Vault. We’ll use Azure Key Vault to access to Event Hubs connection string.

1️⃣ Create Azure Event Hubs

  1. Go to Azure Portal and select Create a resource, type Event Hubs and select click Create.
  2. Fill in the Event Hubs namespace creation details, and then click Create.
  3. Go to the newly created Event Hubs namespace page, select Event Hubs tab from the left pane and + Event Hub:
    • Name your Event Hub as Event Hub
    • Click Create.
  4. Click the name of the Event Hub, and then select Shared access policies and + Add to add a new policy:
    • Give a name to the policy
    • Check Send and Listen
    • Click Create.
  5. After the policy has been created, click the name of the policy to open the details panel, and then copy the Connection string-primary key value. Write it down; you’ll need it for the next step.
  6. Go to Consumer groups tab in the left pane and select + Consumer group, give a name for your consumer group as onboarding and select Create.

2️⃣ Create Azure Key Vault

  1. Go to Azure Portal and select Create a resource, type Key Vault and select Create.
  2. Fill in the Key Vault creation details, and then click Review + Create.
  3. Go to newly created Key Vault and select Secrets tab from the left pane and click + Generate/Import:
    • Give a name to the secret
    • For the value, paste in the connection string you generated at the Event Hubs step
    • Click Create
    • Copy the name of the secret.
  4. Select Access Policies from the left pane and + Add Access Policy:
    • For Secret permissions, select Get
    • For Principal, select Microsoft Graph Change Tracking
    • Click Add.
  5. Select Overview tab from the left pane and copy the Vault URI.

🪡 Exercise: Subscribe to users resource to receive change notifications by using Azure Functions

To start receiving Microsoft Graph Change Notifications, we’ll need to create subscription to the resource that we’d like to track. We’ll use Azure Functions to create subscription.

To create subscription for Microsoft Graph Change Notifications, we’ll need to make a http post request to Microsoft Graph requires Azure Active Directory authentication make API calls. First, we’ll need to register an app to Azure Active Directory, and then we will make the Microsoft Graph Subscription API call with Azure Functions.

1️⃣ Create an app in Azure Active Directory

  1. In the Azure Portal, go to Azure Active Directory and select App registrations from the left pane and select + New registration. Fill in the details for the new App registration form as below:
    • Name: Graph Subscription Auth
    • Supported account types: Accounts in any organizational directory (Any Azure AD directory – Multitenant) and personal Microsoft accounts (e.g. Skype, Xbox)
    • Select Register.
  2. Go to newly registered app in Azure Active Directory, select API permissions:
    • Select + Add a permission and Microsoft Graph
    • Select Application permissions and add User.Read.All and TeamMember.ReadWrite.All.
    • Select Grant admin consent for the organization
  3. Select Certificates & secrets tab from the left pane, select + New client secret:
    • Choose desired expiry duration
    • Select Add
    • Copy the value of the secret.
  4. Go to Overview from the left pane, copy Application (client) ID and Directory (tenant) ID.

2️⃣ Create subscription with Azure Functions

  1. Open Visual Studio Code, open the pallete by clicking CTRL + SHIFT + P on Windows or CMD + SHIFT + P on Mac, search for "create function" and choose Azure Functions: Create Function:

    • A window will pop-up with a message "you must have a project open to create function", select Create new project. Create a new folder and select the folder for your project
    • Select JavaScript as a project language
    • Select Timer Trigger as a template for your project’s first function.
    • Name your Timer Trigger as SubscriptionFunction and press enter.
    • Specify schedule as 0 */61 * * * * and press enter
    • Select Open in current window and press enter.
  2. Select Terminal from the menu bar on top and select New Terminal. Run the following commands in the terminal to install the dependencies:

    npm install @azure/identity @microsoft/microsoft-graph-client isomorphic-fetch readline-sync
  3. Create a folder under the project and name as Shared.

  4. Create a new file inside the Shared folder, name as dateTimeFormat.js, copy the entire code in dateTimeFormat.js inside your file to define the expiration date of the subscription.

  5. Create a new file inside the Shared folder, name as Graph.js. Add the following authentication code snippet inside the Graph.js:

    const expiry = require('./dateTimeFormat');
    const azure = require('@azure/identity');
    const graph = require('@microsoft/microsoft-graph-client');
    const authProviders = require('@microsoft/microsoft-graph-client/authProviders/azureTokenCredentials');
    let _clientSecretCredential = undefined;
    let _appClient = undefined;
    let _expiry = undefined;
    function ensureGraphForAppOnlyAuth() {
    if (!_clientSecretCredential) {
        _clientSecretCredential = new azure.ClientSecretCredential(
    if (!_appClient) {
        const authProvider = new authProviders.TokenCredentialAuthenticationProvider(
        _clientSecretCredential, {
            scopes: [ '' ]
        _appClient = graph.Client.initWithMiddleware({
        authProvider: authProvider

    Replace <YOUR-AAD-APP-TENANT-ID>, <YOUR-AAD-APP-CLIENT-ID> and <YOUR-AAD-APP-CLIENT-SECRET> with the registered app details in the previous step

  6. Add the following function inside Graph.js to make a REST API request to Microsoft Graph /subscriptions endpoint and create a subscription to track new users:

    async function postSubscriptionAsync() {
        _expiry = await expiry.getDateTimeAsync();
        const subscription = {
            changeType: 'created, updated',
            notificationUrl: 'EventHub:https://<YOUR-VAULT-URI>/secrets/<YOUR-KEY-VAULT-SECRET-NAME>?tenantId=<YOUR-TENANT-ID>',
            resource: 'users',
            expirationDateTime: _expiry,
            clientState: 'secretClientValue',
        return _appClient?.api('/subscriptions')
    module.exports.postSubscriptionAsync = postSubscriptionAsync;

    In notificationUrl, make sure to replace <YOUR-VAULT-URI> with the vault uri, <YOUR-KEY-VAULT-SECRET-NAME> with the secret name and <YOUR-TENANT-ID> with the tenant id that you copied from the Key Vault.

  7. Go to SubscriptionFunction > index.js and copy the following references on top of the page:

    const graph = require('../Shared/graph');
  8. In the index.js, copy the following code snippet inside the function to trigger the subscription every 61 minutes:

        const subscription = await graph.postSubscriptionAsync();
  9. Go to local.settings.json, replace the existing code with the code snippet below:

    "IsEncrypted": false,
    "Values": {
        "AzureWebJobsStorage": "UseDevelopmentStorage=true",
    "watchDirectories": [ "Shared" ]
  10. For the testing purposes only, go to SubscriptionFunction > function.json and add the following parameter inside the binding:

    "runOnStartup": true

    Make sure to remove this parameter for the production.

  11. Run the Microsoft Azure Storage Emulator and run the following command on the Visual Studio Code terminal to test your function:

    func host start

When subscription function runs successfully, it will create a subscription for users resource. Azure Event Hubs will receive notifications whenever there is a new user created in Azure Active Directory.

♾️ Exercise: Create Onboarding Function

We’ll create a second function in the project to receive change notifications from Event Hubs when there is a new user created in the Azure Active Directory and add new user in Onboarding team on Microsoft Teams.

  1. Open the patlete on Visual Studio by clicking CTRL + SHIFT + P on Windows or CMD + SHIFT + P on Mac, search for "create function" and choose Azure Functions: Create Function:

    • Select Azure Event Hub trigger as a template for your function
    • Name your Event Hub trigger as OnboardingFunction and press enter
    • Select + Create new local app setting
    • Select your Event Hub settings that you created in the previous steps:
      • Azure subscription
      • Event Hub Namespace
      • Event Hub
      • Event Hub policy
      • Consumer group
    • Press enter.
  2. Go to Shared > Graph.js, add the following parameter on top of the page:

    let _memberId = undefined;
  3. Inside Graph.js, copy the following code to automatically add the new user to the Onboarding team on Microsoft Teams:

    async function postTeamsMemberAsync(memberId) {
        _memberId = memberId;
        const user = '\'' + _memberId +'\')';
        const conversationMember = {
            '@odata.type': '#microsoft.graph.aadUserConversationMember',
            roles: ['owner'],
            'user@odata.bind': user
        return _appClient?.api('/teams/<YOUR-ONBOARDING-TEAM-ID>/members')
    module.exports.postTeamsMemberAsync = postTeamsMemberAsync;

    Make sure to replace <YOUR-ONBOARDING-TEAM-ID> with the team id that you’d like to add your users as a member. You can login to Microsoft Graph Explorer and run my joined teams sample query to view available team ids.

  4. Go to OnboardingFunction > index.js and copy the following references on top of the page:

    const graph = require('../Shared/graph');
  5. In the index.js, and replace the code inside the function with the following code snippet:

     eventHubMessages.forEach(async (message, index) => {
        var jsonMessage = JSON.parse(message);
        for (let i in jsonMessage.value) {
            var resourceData = jsonMessage.value[i].resourceData;
            const newMemberId =;
            await graph.postTeamsMemberAsync(newMemberId);

🚀 Debug your onboarding experience

To debug our onboarding experience, we’ll need run our functions locally and create a new user in Azure Active Directory to see if the new user is added automatically in Microsoft Teams Onboarding team.

  1. Open the terminal in Visual Studio Code and run your functions with the following command:

    func host start

    Make sure that Microsoft Azure Storage Emulator is running in the background.

  2. Go to Azure Portal and select Azure Active Directory from the left pane and go to Users. Select + New user and Create new user. Fill in the details as below:

    • User name: JaneDoe
    • Name: Jane Doe

Add new user in Azure Active Directory

  1. When you added Jane Doe as a new user, it should trigger the OnboardingFunction to run.

Once the OnboardingFunction runs successfully, you should be able to see Jane Doe as a member of the Onboarding team on Microsoft Teams! 🥳 New member in the onboarding team

Source code for this solution can be found in the following GitHub Repository: Onboarding-Functions

📚 Resources

Let people try your query in Microsoft Graph Explorer

Microsoft Graph Explorer is a wonderful learning space for the ones who are looking for testing Microsoft Graph APIs and reviewing the responses quickly. It provides the simple authentication where you can login, then see the response preview with your own tenant data. The best part of Microsoft Graph Explorer is its user-friendly design that makes it practical and easy to understand how to benefit the most out of it. Even better, it continues evolving with new releases all the time!

Today, we will explore one of the most practical features of Graph Explorer: “Share Query“. Let’s say that you are working with advanced queries ($filter, $search, $orderby etc.) in the Graph Explorer. After getting the required results, you would like to let people try your current query. We can easily do that in 2 steps:

  • Step 1: Click on Share button on the right side of the Response preview section.
  • Step 2: Copy your query and share with other people.
  • Result: Others can paste this shared link to any browser, then they will be directed to your pre-populated query in Microsoft Graph Explorer. They can click on Run Query button to see the response preview.

Here is a sample query, feel free to copy and paste it in any browser to see the results in the Graph Explorer:$filter=startswith(displayName,’all’)&method=GET&version=v1.0&GraphUrl=

Feel free to ask you questions and share your experience in the comment window.


Microsoft Graph + Power Automate = M365 data with no code!

Microsoft Graph provides a single endpoint to get connected with M365 data. We know that Power Automate has many built-in MS Graph components to access Outlook, Planner, Calendar and more. But, think about calling Microsoft Graph API with custom filters from Power Automate directly! It is even more exciting and gives us more flexibility and numerous automation possibilities with no-code. Today, our scenario is to get “members” of a particular group in 3 quick steps.

Step 1: Register an application in Azure Active Directory

  • Go to Azure Portal.
  • Under Azure Active Directory, go to App Registration and click on New Registration.
  • Give a name to your app, choose the access level and hit Register button.
  • Go to API permissions tab, click on Add a permission, select Microsoft Graph and then Application permissions, add the following permissions: “Group.Read.All”, “Group.ReadWrite.All”, “User.Read.All”, “GroupMember.ReadWrite.All”, “User.ReadWrite.All”, “Directory.ReadWrite.All”.
  • After creating the permissions, we need to grant consent to the application to allow the application to access Graph API.
  • Go to Certificates & secrets and create a new client secret and copy in a notepad.
  • Finally, go to Overview tab, copy Application (client) ID and Directory (tenant) ID to a notepad, we will need it later.

Step 2: Build Power Automate Flow

  • Go to Microsoft Power Automate Portal.
  • Click on Create tab and choose Instant flow.
  • Give a flow name and choose When an HTTP request is received as a trigger of the flow, then click Create.
  • Extend When a When an HTTP request is received block and click on Use sample payload to generate schema, then add the following schema:
    "type" : "object",
    "properties" : {
       "groupId" : {
          "type" : "string"
  • Then click Save.
  • Click New Step and add Initialize variable with the following details:
    • Name: application_id
    • Type: string
    • Value: AAD App – Application (Client) Id
  • Click New Step and add Initialize variable with the following details:
    • Name: directory_id
    • Type: string
    • Value: AAD App – Directory (Tenant) Id
  • Click New Step and add Initialize variable with the following details:
    • Name: secret
    • Type: string
    • Value: AAD App secret
  • Click New Step and add HTTP with the below details:

Step 3: Test the Flow with Microsoft Graph Explorer and Postman

  • Go to Microsoft Graph Explorer.
  • Sign-in with your account.
  • Find all groups under my organization under Sample queries and click on it.
  • Copy one of the group ids for the testing purposes, we will use it in.
  • You may use Postman for testing purposes, and specify the following details:
    • Method: Post
    • Endpoint: copy it from the first step of your flow (When a HTTP request is received)
    • Header:
      • Key: Content-type
      • Value: application/json
    • Body: { “groupId” : “copied-groupid-from-GraphExplorer“}
  • Run test from Power Automate and send the post request from Postman.

After the successful flow, we should receive the output with all the members’ information in Json format under HTTP block.


– Ayca