Build Python apps with Microsoft Graph

Add user authentication

In this section you will extend the application from the previous exercise to support authentication with Azure AD. This is required to obtain the necessary OAuth access token to call the Microsoft Graph. In this step you will integrate the Azure Identity client library for Python into the application and configure authentication for the Microsoft Graph SDK for Python (preview).

The Azure Identity library provides a number of TokenCredential classes that implement OAuth2 token flows. The Microsoft Graph SDK uses those classes to authenticate calls to Microsoft Graph.

Configure Graph client for user authentication

In this section you will use the DeviceCodeCredential class to request an access token by using the device code flow.

  1. Open graph.py and replace its entire contents with the following code.

    from configparser import SectionProxy
    from azure.identity import DeviceCodeCredential
    from msgraph import GraphServiceClient
    from msgraph.generated.users.item.user_item_request_builder import UserItemRequestBuilder
    from msgraph.generated.users.item.mail_folders.item.messages.messages_request_builder import (
        MessagesRequestBuilder)
    from msgraph.generated.users.item.send_mail.send_mail_post_request_body import (
        SendMailPostRequestBody)
    from msgraph.generated.models.message import Message
    from msgraph.generated.models.item_body import ItemBody
    from msgraph.generated.models.body_type import BodyType
    from msgraph.generated.models.recipient import Recipient
    from msgraph.generated.models.email_address import EmailAddress
    
    class Graph:
        settings: SectionProxy
        device_code_credential: DeviceCodeCredential
        user_client: GraphServiceClient
    
        def __init__(self, config: SectionProxy):
            self.settings = config
            client_id = self.settings['clientId']
            tenant_id = self.settings['tenantId']
            graph_scopes = self.settings['graphUserScopes'].split(' ')
    
            self.device_code_credential = DeviceCodeCredential(client_id, tenant_id = tenant_id)
            self.user_client = GraphServiceClient(self.device_code_credential, graph_scopes)
    

    This code declares two private properties, a DeviceCodeCredential object and a GraphServiceClient object. The __init__ function creates a new instance of DeviceCodeCredential, then uses that instance to create a new instance of GraphServiceClient. Every time an API call is made to Microsoft Graph through the user_client, it will use the provided credential to get an access token.

  2. Add the following function to graph.py.

    async def get_user_token(self):
        graph_scopes = self.settings['graphUserScopes']
        access_token = self.device_code_credential.get_token(graph_scopes)
        return access_token.token
    
  3. Replace the empty display_access_token function in main.py with the following.

    async def display_access_token(graph: Graph):
        token = await graph.get_user_token()
        print('User token:', token, '\n')
    
  4. Build and run the app. Enter 1 when prompted for an option. The application displays a URL and device code.

    Python Graph Tutorial
    
    Please choose one of the following options:
    0. Exit
    1. Display access token
    2. List my inbox
    3. Send mail
    4. Make a Graph call
    1
    To sign in, use a web browser to open the page https://microsoft.com/devicelogin and
    enter the code RB2RUD56D to authenticate.
    
  5. Open a browser and browse to the URL displayed. Enter the provided code and sign in.

    Important

    Be mindful of any existing Microsoft 365 accounts that are logged into your browser when browsing to https://microsoft.com/devicelogin. Use browser features such as profiles, guest mode, or private mode to ensure that you authenticate as the account you intend to use for testing.

  6. Once completed, return to the application to see the access token.

    Tip

    For validation and debugging purposes only, you can decode user access tokens (for work or school accounts only) using Microsoft's online token parser at https://jwt.ms. This can be useful if you encounter token errors when calling Microsoft Graph. For example, verifying that the scp claim in the token contains the expected Microsoft Graph permission scopes.