question

jan-tosovsky avatar image
1 Vote"
jan-tosovsky asked PathepuramNaveenINFOSYSLIMITED-6415 answered

Sending emails from daemon app using Graph API on behalf of me

I'd like to send some internal alerts or notifications from my daemon scripts directly to specific email addresses.

I am investigating simple REST API client using Microsoft Graph API, but I am failing to find any example covering this simple scenario.

For daemon apps AFAIK only Client Credentials authentication provider is available.
https://docs.microsoft.com/en-us/graph/sdks/choose-authentication-providers

In this case:
- application-wide Email.Send scope needs to be allowed
- this scope allows to send emails on behalf of anybody !
- because of this broad permission the consent of tenant Admin is required

This broad permission is not acceptable in our company so no way.

I hope I am missing something and there is some way.

azure-ad-graph
5 |1600 characters needed characters left characters exceeded

Up to 10 attachments (including images) can be used with a maximum of 3.0 MiB each and 30.0 MiB total.

soumi-MSFT avatar image
0 Votes"
soumi-MSFT answered soumi-MSFT commented

@jan-tosovsky, Thank you for reaching out and I apologize for the delay in my response. based on this query you shared, I believe the best way to go about is using the on-behalf-of flow. When you go through the details of this flow you would find that initially a user has to first authentication and fetch a token for an API registered in AAD (lets say API-A) and then this API-A would be making the call to the Graph API on behalf of the user.


Initially, when the user has to authenticate to get a token for API-A, since you are using a Daemon app, you can use the ROPC flow where you can specify the username and password in the app code itself using which the token can be requested from AAD.


Now, when using the on-behalf-of flow, you would need to provide delegated permission "Send mail as a user", for graph api on API-A so that it can fetch a token for Graph API on your behalf.


Another approach you could use here to avoid having to grant these rights to all users (which would allow them to send via Outlook, etc.) would be to have your backend app use the client credentials flow to get an app-only token. In that case, the app itself would have the permission to send as any user.


Hope this helps.


Do let us know if this helps and if there are any more queries around this, please do let us know so that we can help you further. Also, please do not forget to accept the response as Answer; if the above response helped in answering your query.




· 1
5 |1600 characters needed characters left characters exceeded

Up to 10 attachments (including images) can be used with a maximum of 3.0 MiB each and 30.0 MiB total.

@jan-tosovsky, Just wanted to check if the above response helped in answering your query. Do let me know if there are any more queries around this so that we can help you further.

0 Votes 0 ·
PathepuramNaveenINFOSYSLIMITED-6415 avatar image
0 Votes"
PathepuramNaveenINFOSYSLIMITED-6415 answered

@soumi-MSFT I have a same issue and here is my case

I have a service account using which i need to send Email

I created a appId and got Send.Mail delegation consented by AAD Admin

33929-image.png



This is the error I am getting when sending the Email. I spent lot of time trying to know what is the issue. Can you please help me what is the problem.

Federated service at https://msft.sts.microsoft.com/adfs/services/trust/2005/usernamemixed returned error: ID3242: The security token could not be authenticated or authorized.

This is the code I am using to get the token.



string[] scopes = new string[] { "Mail.Send" };

             IPublicClientApplication publicClientApplication = PublicClientApplicationBuilder
                         .Create(clientId)
                         .WithTenantId(tenantId)
                         .Build();

             UsernamePasswordProvider authProvider = new UsernamePasswordProvider(publicClientApplication, scopes);
               
             GraphServiceClient graphClient = new GraphServiceClient(authProvider);




And below is the code to send Email.



SecureString password = new SecureString();
foreach (char c in emailpassword)
{
password.AppendChar(c);
}

             // construct http request
             var message = new Message
             {
                 Subject = subject,
                 Body = new ItemBody
                 {
                     ContentType = BodyType.Html,
                     Content = body
                 },
                 ToRecipients = new List<Recipient>()
                 {
                     new Recipient
                     {
                         EmailAddress = new EmailAddress
                         {
                             Address = toEmailId
                         }
                     }
                 }
             };

             if (ccMailId != null)
             {
                 message.CcRecipients = new List<Recipient>()
                 {
                     new Recipient
                     {
                         EmailAddress = new EmailAddress
                         {
                             Address = ccMailId
                         }
                     }
                 };
             }

             var saveToSentItems = false;

             await graphClient.Me.SendMail(message, saveToSentItems).Request().WithUsernamePassword(email, password).PostAsync();




image.png (3.7 KiB)
5 |1600 characters needed characters left characters exceeded

Up to 10 attachments (including images) can be used with a maximum of 3.0 MiB each and 30.0 MiB total.