1
votes

In order to operate OneNote with azure's daemon app, I created a new ClientID, acquired the Access Token by user authentication with that ClientID, and realized access to the OneNote API using it.

However, instead of user authentication, Access token is acquired by ClientID and certificate, and access to OneNote API using it is refused.(401 Unauthorized)

How can I operate OneNote from azure dameon App?


The way I tried

The AccessToken creation by the certificate was implemented with reference to the following. https://azure.microsoft.com/ja-jp/resources/samples/active-directory-dotnet-daemon-certificate-credential/

Specific AccessToken acquisition codes are as follows,

public  async Task AuthWithCertAsync(string tenant, string clientID, string certName)
{
    var authority = $"{aadInstance}{tenant}";
    var authContext = new AuthenticationContext(authority);

   //refer: above URL
   ClientAssertionCertificate certCred = GetCertificate(clientID, certName);
   if (certCred == null) {return false;}

   //"https://graph.microsoft.com/";
   var graphResult = await authContext.AcquireTokenAsync(graphResourceID, certCred);
   graphToken = graphResult.AccessToken;

   //"https://www.onenote.com/";
   var onenoteResult = await authContext.AcquireTokenAsync(onenoteResourceID, certCred);
   onenoteToken = onenoteResult.AccessToken;
}

With this graphToken, access to the Graph API succeeds.

    using (var client = new HttpClient())
    {
        client.DefaultRequestHeaders.Add("Authorization", $"Bearer {graphToken}");
        //e.g. "https://graph.microsoft.com/v1.0/groups", "https://graph.microsoft.com/v1.0/users"
        var response = await client.GetStringAsync(url);
        ...
    }

However, if the target URL is an API on onenote, it fails.

    using (var client = new HttpClient())
    {
        client.DefaultRequestHeaders.Add("Authorization", $"Bearer {graphToken}");
        //e.g:"https://graph.microsoft.com/beta/users/{userID}/notes/notebooks"
        // Occured HttpRequestException(401 Unauthorized)
        var response = await client.GetStringAsync(url);     
        ...
    }

This request returns HTTP 401 Unauthorized status.

Also when accessing OneNote API on onenoteToken failed.

    using (var client = new HttpClient())
    {
        client.DefaultRequestHeaders.Add("Authorization", $"Bearer {onenoteToken}");
        //e.g.:"https://www.onenote.com/api/v1.0/users/{userID}/notes/notebooks"
        var response = await client.GetStringAsync(url);
        return response;
    }

This request also returns HTTP 401 Unauthorized status.


The application setting in Azure Active Directory:

  • Type:
    • WEB APPLICATION AND/OR WEB API
  • Multi Tenant:
    • ON
  • permissions to other applications:
    • Graph, OneNote, Active Directory, SharePoint :Application Permissions all checked.

In the admin account of the target tenant, the following admin consent URL is accessed and accepted.

https://login.microsoftonline.com/common/adminconsent?client_id={clientID}&state={state}&redirect_uri={redirectUrl}

Update

According to the answer of https://stackoverflow.com/a/41890179/1411521, I understood that there is no way to access OneNote by daemon App with the current Graph API. (at 2017-1-31)

However, Application Permission of OneNote API can set as follows.

  • View and modify notes for all users
  • View notes for all users

Despite the fact that they are valid, what causes the authentication error (401 Unauthorized) with the following code?

  using (var client = new HttpClient())
  {
    client.DefaultRequestHeaders.Add("Authorization", $"Bearer {onenoteToken}");
    //e.g.:"https://www.onenote.com/api/v1.0/users/{userID}/notes/notebooks"
    var response = await client.GetStringAsync(url);     // Occured HttpRequestException(401 Unauthorized)
    ...
  }
2
Please clarify on what errors you were receiving, or what you mean by "failed"Jamie Phan

2 Answers

1
votes

You were mixing the Microsoft Graph and OneNote API.

The token you were acquire is for the Microsoft Graph REST, and you can manipulate the OnenNote through Microsoft Graph REST which in beta version by following the document here(beta reference->OneNote).

And if you want to use the OneNoe API, you can refer the document here for the authentication.

Update

To list the notebooks, we need permissions like Notes.Read, Notes.ReadWrite.CreatedByApp, Notes.ReadWrite, Notes.Read.All, or Notes.ReadWrite.All. However there is no such kinds of permission for the Client Credential flow for Microsoft Graph. enter image description here If you want the Microsoft Graph to support the Client Credential flow to manipulate the OneNote, you can submit the feedback from here.