I'm building an internal meeting room app that uses the Microsoft Graph API and I would like to extend Event objects with a Schema Extension.
Documentation:
API Reference
Tutorial Example
However when running a query to register a new schema extension, I am receiving this HTTP response:
{
"url": "https://graph.microsoft.com/beta/schemaExtensions",
"status": "403 Forbidden",
"headers": {
"request-id": "e1e36210-6c4c-4ed8-afb1-c9ee6f6362ed",
"client-request-id": "e1e36210-6c4c-4ed8-afb1-c9ee6f6362ed",
"x-ms-ags-diagnostic": "{\"ServerInfo\":{\"DataCenter\":\"North Europe\",\"Slice\":\"SliceA\",\"ScaleUnit\":\"001\",\"Host\":\"AGSFE_IN_2\",\"ADSiteName\":\"DUB\"}}",
"duration": "742.4624"
},
"body": {
"error": {
"code": "Authorization_RequestDenied",
"message": "Insufficient privileges to complete the operation.",
"innerError": {
"request-id": "e1e36210-6c4c-4ed8-afb1-c9ee6f6362ed",
"date": "2017-05-10T10:05:37"
}
}
}
}
I can confirm that my application has the prerequisite scope permission of Directory.AccessAsUser.All and it's also been more than 16 hours since adding this permission. I have also got verified domains, so the namespace should be OK per the documentation reference.
My API query in code:
Outlook.test({
version: 'beta',
resource: 'schemaExtensions',
method: 'POST',
body: {
id: 'thehivegroup_beethere',
description: 'Extension for event presence status',
targetTypes: [ 'Event' ],
properties: [
{ name: 'checkIn', type: 'String' },
{ name: 'checkOut', type: 'String' }
]
}
})
.then(result => console.log(result), err => console.error(err))
Which results in a POST with the JSON encoded in the body and headers with authorization token to the URL https://graph.microsoft.com/beta/schemaExtensions.
I have tried different IDs, such as beethere, which resulted in a namespace error, so I know this ought to be working fine.
There are no other scope permissions I am aware of that I need to enable here as well. The error is just too vague for me to figure out what privileges are insufficient here.
EDIT: Have manually run the query in the Graph Explorer as an Admin in the tenant, added the scope permissions required for the API and some extra ones in case, but the query for registration of Schema Extensions still does not work, with the same error message as the application receives. So it is definitely not a problem in my code, but the Microsoft Graph API. Is there a contact or way to ask microsoft to look into the issue?
Directory.AccessAsUser.All is a delegated permission only (it must be delegated because it grants access to directory based APIs as the signed-in user's access rights). It doesn't show up in the roles claim because it isn't an application permission.
As far as I know, right know, you cannot use the application flow (client credentials) to create a schema extension, and you need to use the "code authorization" flow. Please let us know if this is a requirement. Additionally we'd love to know if you want to see an experience for schema definition registration as part of the application registration...
Also you CANNOT currently create a schema extension definition (or manage it) through Graph Explorer. For you to created a definition, you must either be an admin or the owner of the app creating the extension definition AND the creation request must also come from that application (which cannot be graph explorer). We may look at relaxing this last constraint.
If you want to see a code snippet for this it's available here (although it's a UWP c# app, not JS): https://github.com/microsoftgraph/uwp-csharp-snippets-rest-sample.
Also schema extensions is now GA, and available in the v1.0 endpoint.
Hope this helps,
Graph Explorer is able to add an extension.
You will need to create an app in your tenant and set the owner in the payload to the client id of your app.
more on this
This schema extensions creating REST works well for me. Please ensure that the token contains Directory.AccessAsUser.All permission. You can parse the token check the scp claim in it from this site.
Related
I'm trying to call the Graph API: https://graph.microsoft.com/v1.0/me/sendMail.
I run the query successfully with the Graph Explorer, where I gave my user the Mail.Send permission. And if I use the Access Token from the Graph Explorer in Postman it works too.
But if I use my own Access Token which I create from calling the Azure Active Directory App in ends in this error:
{
"error": {
"code": "RequestBodyRead",
"message": "The property 'subject' does not exist on type 'Microsoft.OutlookServices.Message'. Make sure to only use property names that are defined by the type or mark the type as open type. REST APIs for this mailbox are currently in preview. You can find more information about the preview REST APIs at https://dev.outlook.com/.",
"innerError": {
"date": "2021-12-23T12:47:23",
"request-id": "cbb00b85-295b-45e2-abc7-f064ec52f994",
"client-request-id": "cbb00b85-295b-45e2-abc7-f064ec52f994"
}
}
The body in the message is the same, I just changed the Access Token from the Graph Explorer to the one I created. The Access Token is created through a POST Request to:
POST https://login.microsoftonline.com/{tenant}/oauth2/v2.0/token HTTP/1.1
Host: login.microsoftonline.com
Content-Type: application/x-www-form-urlencoded
client_id=535fb09-9f3-476-9bf-4f126479986
&scope=https%3A%2F%2Fgraph.microsoft.com%2F.default
&client_secret=qWgdYAmab0YSkuL1qPX
&grant_type=client_credentials
I checked both Tokens with https://jwt.io/ if they vary in some way. The only thing which was odd was the parameter "aud" for Audience. The value in my Token was different than the one from the Graph Explorer, but I don't know if I can change that.
The Azure Active Directory App does have the necessary permissions, also with Admin consens.
enter image description here
Help is much appreciated.
You have given Delegated permissions to the application which allow your app to call an API on behalf of a user.
But you authenticate using only application credentials where no user is involved.
In that case only Application permissions apply.
You either need to grant the "Send mail as any user" Application permission (and use /users/user-id instead of /me), or you need to change how you authenticate such that it involves a user at some point of the process.
I've been using Microsoft Graph API to create users in Azure Active Directory, but when I try to update skills or schools I get error:
PATCH https://graph.microsoft.com/v1.0/me
{
"skills": ["skills-value"]
}
{
"error": {
"code": "BadRequest",
"message": "Tenant does not have a SPO license.",
"innerError": {
"request-id": "804948b5-f087-4be8-bdf0-ab49dccf7efc",
"date": "2018-04-14T17:55:52"
}
}
}
Also when I try to update for example businessPhones it's work fine, I get no errors.
PATCH https://graph.microsoft.com/v1.0/me
{
"businessPhones": ["businessPhones-value"],
}
HTTP/1.1 204 No Content
Any idea?
The Microsoft Graph is a front-end which intelligently wraps a suite of Microsoft and Office 365 APIs into a single endpoint. This includes free and paid services, and ultimately to access certain APIs you will need to have a subscription for the services which host the underlying API.
In this case, you are seeing that the skills attribute on the user is stored in SharePoint Online, and if you do not have a SharePoint license, you will not be able to use that property.
If you are simply looking for a way around this, you might look into storing and retrieving your skill information using Add custom data to resources using extensions which is stored in Azure AD and should be totally free to access.
I'm trying to develop an app in my enterprise and I've followed this tutorial to get access to the AD users information. Meaning:
I created an app in https://apps.dev.microsoft.com/
I set User.Read.All in Application Permissions and User.Read in Delegated Permissions
With this done I'm able to successfully login (Azure AD OAuth2 with https://graph.microsoft.com/ as resource and User.Read as scope) and get a correct response from https://graph.microsoft.com/v1.0/me.
Ask the Admin for the Delegated Permissions
With this, my admin can see in the azure portal that my App has both permissions consented by himself.
This is working because I asked a coworker to log in and I could get a correct response from https://graph.microsoft.com/v1.0/me even though he wasn't even prompted to consent this (Before the admin consenting the permissions the user was prompted)
Request a token from https://login.microsoftonline.com/common/oauth2/token with client_credentials as a response_type
Receive the token!
Do a GET request to https://graph.microsoft.com/v1.0/users and receive:
{
"error": {
"code": "Authorization_IdentityNotFound",
"message": "The identity of the calling application could not be established.",
"innerError": {
"request-id": "b2d9ec62-0b65-44eb-9e0f-4aec52b45750",
"date": "2017-03-22T19:19:48"
}
}
}
Furthermore, doing a request to https://graph.microsoft.com/v1.0/me returns:
{
"error": {
"code": "BadRequest",
"message": "Current authenticated context is not valid for this request",
"innerError": {
"request-id": "047e2ba9-a858-45fc-a0dd-124e1db503f3",
"date": "2017-03-22T19:39:25"
}
}
}
Which leads me to believe that Microsoft knows this token and knows it is not impersonating any user.
I've been looking for documentation on Azure AD and Microsoft Graph authentication but I only find blog posts and all seem outdated (although most features are in preview).
If you could point me in the right direction I would thank you.
I've also found this and this similar questions on SO but they all remain unanswered.
Update, after this answer
Thank you, Dan,
I've used my organization domain name and I'm also able to get a token.
Now the response from https://graph.microsoft.com/v1.0/users/ is:
{
"error": {
"code": "Authorization_RequestDenied",
"message": "Insufficient privileges to complete the operation.",
"innerError": {
"request-id": "3f190b47-73f5-4b29-96f9-54ed3dbc3137",
"date": "2017-03-23T11:07:15"
}
}
}
Which makes no sense because in the azure portal I have User.Read.All as Application Permission (already consented by the admin).
I think the problem is with the request for the token, that returns successfully no matter the scope I send, even if I made one up.
For Example:
POST https://login.microsoftonline.com/<domain>/oauth2/token
client_id:*******
client_secret:*******
resource:https://graph.microsoft.com/
grant_type:client_credentials
scope:Foo.Bar
Returns:
{
"token_type": "Bearer",
"expires_in": "3599",
"ext_expires_in": "0",
"expires_on": "1490271617",
"not_before": "1490267717",
"resource": "https://graph.microsoft.com/",
"access_token": *****
}
I had two problems, both not covered documentation:
For client credentials, if the app belongs to a work or school (organization) context then for https://login.microsoftonline.com/common/oauth2/token replace common with a tenantId or domain name (thanks to Dan Kershaw)
For https://graph.microsoft.com/v1.0/users or https://graph.microsoft.com/v1.0/users/{id | userPrincipalName} you need Directory.Read.All permission.
Note:
User.Read.All is relevant for Microsoft to stop requesting permissions (delegation) to the user when you ask for User.Read in the OAuth workflow. Check this and other Permission related issues in the Release Notes.
I've added this issue to the Microsoft Graph Docs!
The /me segment is a shortcut or alias for the currently signed-in user. The request to /me will never work with an application token, because it doesn't contain any user context (or signed in user) - and hence the error. We might be able to improve this error though ;)
I believe when using the client credentials flow, you need to specify the actual tenant that you want a token for.
If you're app is performing this operation in a work or school (organization) context then for https://login.microsoftonline.com/common/oauth2/token replace common with a tenantId or domain name, and see if that works.
If you are following https://learn.microsoft.com/en-us/azure/active-directory/develop/active-directory-v2-protocols-oauth-client-creds it looks like we might have a couple of doc bugs in there that we need to fix...
Hope this helps,
I'm trying to implement checking availability for specific user (actually a room) in O365 calendar. I'm using Graph API as it's recommended by Microsoft.
My first approach was using POST on https://graph.microsoft.com/v1.0/me/findMeetingTimes with the message body prepared according to template given in Graph API Explorer. On the API Explorer everything seems to work fine but when I try to run exactly the same request with my applications token I receive 403:
{
"error": {
"code": "ErrorAccessDenied",
"message": "Access is denied. Check credentials and try again.",
"innerError": {
"request-id": "b130177d-e138-4cc7-8e72-5d3529a9dc24",
"date": "2017-03-21T08:47:10"
}
}
}
I checked the app's delegated permissions in AAD and they seem to be fine. For Microsoft Graph those are granted:
Calendars.ReadWrite.Shared
Calendars.Read.Shared
Calendars.ReadWrite
Calendars.Read
I get exactly the same response (403) when I try to simply list user's events: https://graph.microsoft.com/v1.0/users//events In Graph API Explorer 500 is returned.
I found the following bug description: https://github.com/microsoftgraph/microsoft-graph-docs/issues/559 (and probably this one too) Is it related with the issues above?
Any clue what I might be doing wrong?
Is there any other way to achieve the same using different endpoint or API assuming that I still want to use oAuth for authorization?
I will be grateful for any hint
Update: Outlook Calendar API seems to work. Still appreciate any ideas why Graph API doesn't?
The FindMeetingAPI needs A work or a school account . If you are logging in using your personal email ID , you might not be able to login. Moreover , you need to set permissions to Calendars.Read Calendars.Read.All Calendars.ReadWrite User.Read"
We would like to automatically create a project ID and install our ULAPPH Cloud Desktop application using the App Engine Admin API (REST) and Golang.
https://cloud.google.com/appengine/docs/admin-api/?hl=en_US&_ga=1.265860687.1935695756.1490699302
https://ulapph-public-1.appspot.com/articles?TYPE=ARTICLE&DOC_ID=3&SID=TDSARTL-3
We were able to get a token but when we tried to create a project ID, we get the error below.
[Response OK] Successful connection to Appengine Admin API.
[Token] { "access_token" : "TOKEN_HERE", "expires_in" : 3599, "token_type" : "Bearer" }
[Response Code] 403
[Response Body] { "error": { "code": 403, "message": "Operation not allowed", "status": "PERMISSION_DENIED", "details": [ { "#type": "type.googleapis.com/google.rpc.ResourceInfo", "resourceType": "gae.api", "description": "The \"appengine.applications.create\" permission is required." } ] } }
We are just using the REST API calls. Request for token was successful as you can see above and the scope is ok as well. Now, when we posted the request to create application, we are having the error that says "appengine.application.create" permission required.
How do we specify the permission?
What are the possible reasons why we are getting that error? Do we missed to send a field in JSON or in query?
As per below link, we just need to pass the json containing the id and location. We also just need to pass the token in the Authorization header. The same logic I have used successfully in accessing Youtube, Drive APIs etc so not sure what needs to be done since I have followed the docs available.
I have also posted the same issue in Google Groups and now waiting for their reply.
It seems you've given no details about how you set up the account you're using to authorize the request. You'll need to make sure the appengine.applications.create permission is given to the account you're using, as mentioned in the error text. You can use the Google Identity and Access Management (IAM) API for this.
(by the way, I'd given this answer in the original thread, although you didn't reply or seem to take action on it. check it out! this is likely the solution you need!)