2

We have implemented sending emails via graph api.

In microsoft app https://apps.dev.microsoft.com we have created application and for this application set permission 'Mail.Send'.

For authentication we are using way "Get access without a user".

We are receiving token via this url: https://login.microsoftonline.com/our_tenant/oauth2/v2.0/token and body is looks like this:

"client_id=app_id&scope=https%3A%2F%2Fgraph.microsoft.com%2F.default&client_secret=app_secret_key&grant_type=client_credentials"

Mail is sent using this link:

https://graph.microsoft.com/v1.0/users/user_Email/sendMail

In body json with email Object.

When we sent email via this method then receive response code '403' with text "Access is denied. Check credentials and try again."

Before testing it we have created trial account for developed this integration. And with trial account this process have worked perfect.
Could you please help with current problem? Maybe we have forgotten something or have problem with account.

Best regards

vzhutenko
  • 23
  • 3

2 Answers2

6

Whenever you have a problem like this, where you have a token and you believe you SHOULD have access to something, but the API returns 403, the first step should be to parse the access token. You can use https://jwt.io for this, (or any other JWT parser). You want to confirm the following:

  • The aud claim is set to https://graph.microsoft.com
  • The tid claim is a GUID that matches the tenant ID of your Office 365 tenant
  • For app-only token (or as you call it, "get access without a user"): The roles claim is an array of the scopes you expect. In your case, it should include Mail.Send
  • For delegated access tokens (not your case, but included here for completeness): The scp claim is a string that contains the scopes you expect.

My guess here is that you may have a token with no roles claim at all, which is what will happen if an administrator has not provided consent. You can fix that by checking out this section of the Azure article on client credential flow.

Jason Johnston
  • 17,194
  • 2
  • 20
  • 34
  • Hi @JasonJonston, Thank you, it is very useful. I have parsed token, and it has aud, tid, but roles not exist. But i have parsed token for my trial account and everything is included. Configurations for both account are same. Could you please suggest how it can be solved? Best regards – vzhutenko Mar 02 '18 at 07:01
  • Hi @JasonJonston, I understood, Need get adminconent. I will try do it. But it is strange, because for my trial account, I did not do it and it is working without it. Thank you for you help. – vzhutenko Mar 02 '18 at 07:44
  • 1
    It depends how you registered the app and who registered it. It used to be that if your admin was the one that registered the app, that had the added benefit of also recording consent. In recent tests that seems to have changed though, so it seems now it is always required to do the admin consent explicitly. – Jason Johnston Mar 02 '18 at 13:04
1

For the sake of completeness, in addition to the answer provided by @Jason Johnston, for future users who are still having issues like I was, please note the following:

Bonus

  • For parsing tokens, the following website is more informative: https://jwt.ms
  • For validating your application, try using Postman or cURL instead. A quick way to get the cURL parameters is via sending triggering a `sendMail query on Graph Explorer, then copying the HTTP request as cURL if your browser supports it (see below).

Quick cURL from Browser

OthmanEmpire
  • 103
  • 2
  • 7