Microsoft Graph - Scoping Application Mail permissions - azure

I am leveraging the graph api in powershell to automatically send emails to users.
This script is designed to run unattendedly, so i can not impersonate a user by logging in interactively.
In order to do so, i've created a service principal with application* permissions to the mail service of the tenant.
However the mail permissions that can be assigned are far too large, as i don't want this service to be able to send mail as any user.
Is there a way to scope this permission such as my SP could only send mail with a specific service account that i would provision in azure ad, with the constraint of not being able to log in interactively prior to the script execution ?

Having Delegated Mail.Send permissions would limit it to only the delegated user, which sounds like what you're after.
The dilemma though is that are running a PS script (a.k.a. no user involvement). You need user involvement to use Delegated, so yip...
You could contrive something like this:
Setup Delegated permissions for sending mail
Let the user log in once (somewhere) with your service principal, capturing their "refresh token"
Let the PS script lookup the "refresh token" for the user to create an access token
Use access token to send email "that specific" delegated user.
Unfortunately you won't be able to have "Delegated permissions" with no user interaction, so if that's the case, you're going to have to stick with the "wider" app permissions as you currently have.

Related

Proper apps permissions from azure AD to grant access on Microsoft Graph

Proper apps permissions from azure AD to grant access on Microsoft Graph where we can extract users emails information like To, From, Cc, Bcc, Subject.
Tried to grant all access but still encountering an access denied error.
None
Expected result will show users emails information like To, From, Cc, Bcc, Subject.
I suppose you want to use the Microsoft Graph - Get message, it returns the message object which has the properties you want.
If you want to call the Microsoft Graph without a user, you need the Application permission Mail.Read. You just need to create an Azure AD Application and grant the permission for it, the application permission Mail.Read need admin consent, so don't forget to grant admin consent, about consent an application, see this link. For more details about all the steps, see Get access without a user.
If you want to call the Microsoft Graph on behalf of a user, you need the Delegated permission Mail.Read, more details see Get access on behalf of a user.
Besides, if you want to get a message in another user's mail folder, please note the information as below, see Get message.

Consume Microsoft Graph API from backend service (node.js)

I want to send emails using Microsoft Graphs API from a backend service developed in node.js, that has no interactions with the user.
If I understand it correctly from this paragraph, if I use the Get access without user procedure, the administrator will have to give me some rights and then I will have those rights on every user account in the organization. This is not my goal, I only want to have those rights for one specific account, for which I have the login and password.
Is there a way to log in with an office365 account without user interaction?
Thanks :)
No. You need to have the user authenticate in order to obtain the initial access token and refresh token (to refresh your permission to access the account).

Access token and authentication for guest user

TLDR:
is it possible to have guest account, like guest#organization.onmicrosoft.com, at company's MS Office 365 cloud that will have "read" permission to organization's users calendars and events with constant access token? By constant access token I mean that I sign in once for this guest user and receive constant access token from Azure AD (like application access authentication but as guest account).
I have my own company's MS Office 365 account with some users in it. There is one global administrator account and few regular users.
There is second company, let's call it XYZ, with their own MSO365 account with many of administrators and users. Big company.
Now I'm writing simple app where I need to have access to read XYZ company's users calendars and events. I have list of required users in my app with proper MSO365 ID's.
I think that 'read' privilege is enough since we can send invitation for events through ordinary email message.
My App will read user events through MS Graph API etc. with some logic and realease it (send invitations for events etc.) with CRON jobs.
And here is my problem with authentication.
I don't want to have "application access" Azure AD privileges at my App. I know the XYZ company security policy won't apply it since "application access" gives access to all accounts at organization. Application access means that XYZ company's global administrator apply application privileges for my App by single sign in into Azure AD. If he do so i have Access token which i can use for API calls at my app withoud need of additional authentication.
I can't use "user access" Azure AD authentication neither.
Due to my CRON jobs and API calls which fire then.
User access means that user need sign in at Azure AD login service what gives me Access token and Refresh token for API calls. Those tokens are 1 hour lifetime.
So I though about: if there is possibility to have a guest account at XYZ company's MSO365 that would let me use authentication mechanism like the "application access"?
By this I mean that XYZ company's global Admin creates me a guest account like guest#xyz.onmicrosoft.com which will have access to read users calendar and events. What is more I need this account to have constant access token which I can use in my cron job's api calls with no need to sign in at Azure AD.
The question is: is it possible? If so how to do it?
The only way there (AFAIK) is to use refresh tokens.
Application-level access is more robust but requires organization-wide access.
So you use delegated access (user access), store refresh tokens somewhere.
You can use those tokens basically indefinitely,
however certain events can expire the refresh token.
It doesn't happen often, but it can happen.
In that case you would need the user to login again so you can get a new refresh token.
You should also store the new refresh token that you get when you acquire tokens using a refresh token.
This new token can overwrite the old token for that user.
And of course keep in mind refresh tokens are user-specific so you gotta store one for each user.
This is the approach that one of our bigger apps takes.
If we fail to acquire a token in the background process,
that user gets a flag set on them that their token does not work,
and they'll get a notification that they need to re-authenticate for the feature to start working again.

DocuSign Integrator Key permissions

Is there any way to limit the access of an integrator key to a specific security group in DocuSign? For instance I only want to be able to get envelopes created by users who are part of a specific group. Is it possible?
Impose limits on your app by making the individual users log into it. Eg use Authorization Code Grant flow so an individual user will log into the app and then the app will have the individual user's permissions capability.
You should only create a "service integration" if there is no way for a user to log in.
The integration key enables your app to use the api. The integration key does not grant any privileges per se. Privileges are granted by the login used.

Client Credential Flow without Admin login

Following these instructions on implementing client credential flow, using this sample repo to test on, I got a running version of an app using client credential flow that can read email, calendar, contacts.
However I need to sign in with my O365 tenant admin every time I run it and grant access to the application to read emails, calendar, etc.
Isn't the whole point of Client Credential Flow (app-only) that I shouldn't need to enter any credentials to read data, since I've created a certificate that connects my AAD-app with my web-app.
The only thing I can think of is that I have to sign in with the admin just once to set it up properly, but then it makes no sense that I get prompted to login as admin every time I run the application (running on localhost).
You have to run admin consent once, then that should give your app the access it needs with just its client id and secret. Now this only matters to application permissions obviously, if you are using delegated permissions, those always require a logged in user.
To give admin consent, you will need to hit a URL like this in Azure AD:
https://login.microsoftonline.com/common/oauth2/authorize?client_id=your-client-id&redirect_uri=https%3A%2F%2Fwww.company.com%2Fazure-redirect%2F&response_type=code&prompt=admin_consent
Replace your-client-id with your app's client id, and the redirect URI with a reply URL registered for your app (URL-encoded of course). It should prompt you with something like "Do you want to give app AppName the following permissions? No one else in the organization will be asked." You can also replace common with your tenant id or domain name.
You can use the Azure AD Graph Explorer to check if the consent was passed successfully. Check servicePrincipals, find your app, and then check oauth2PermissionGrants and find the objects with your service principal's id. That will tell you what permissions have been granted and on what resources (the Graph API etc.)

Resources