Compartilhar via


Announcing the new version of the Graph API: api-version=2013-11-08

We're excited to announce the next version of the Graph API, api-version=2013-11-08 is now available. There are several updates that can be useful for your applications, and enable some new scenarios.

The major updates in this release include: 

  • Support for provisioning Federated users
  • User License assignment
  • Support for adding multiple members to a Group
  • Managing a Group's Owner
  • Sorting Groups by their Display Name property
  • Additional Differential Query features

1. Provisioning Federated Users, by exposing a new user property: immutableId

We now expose a new user property called “immutableId” through the Graph API. What is the significance of this property?  It is used to associate the on-premises user object account to the cloud user hosted in Azure Active Directory – for example, if you have an on-premise directory, and the user object from that directory has an identifier GUID with a value of “9c5923e9-de52-33ea-88de-7ebc8633b9cc", then the Azure AD User object can store this value in its immutableId property (stored as a string). The immutableId is used to link the on-premises account identity with the Azure AD account identity.  Note: the immutableId value cannot contain spaces or the $ symbol.

Note: customers using the Microsoft DirSync tool, will automatically have sync’ed Azure AD Users’ immutableId property populated – DirSync writes this value as the base64 encoded value of the on-premises object Guid.  Application should store the value that meets the requirements of their federated identity service provider

Here’s an example GET call, requesting only a user’s immutableId property: 

GET https://graph.windows.net/contoso.com/users/Adam@contoso.com/immutableId?api-version=2013-11-08

RESPONSE (in JSON):   {   “value”:”6SNZnFLe6jOI3n68hjO5zA==”   }

If you are creating an Azure AD User, and are using a federated domain for the User’s userPrincipalName property, then you must specify a value for the user’s immutableId property – for example, this is the POST operation to create a new user, assigning @Fabrikam.com to the user’s userPrincipalName, which is configured as a federated domain.

Creating a New User using a federated  domain “Fabrikam.com”

POST

https://graph.windows.net/Contoso.com/users?api-version=2013-11-08

HEADERS:

Content-Type: application/json

Authorization: Bearer eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiIsIng1dCI6Ik5HVEZ2ZEstZnl0aEV1T….

BODY


 {        "accountEnabled":true,    "userPrincipalName":Derek@Fabrikam.com,    "displayName":"Derek ",      "mailNickname":"Derek",

     "passwordProfile":{ "password":"placeHold3r$", "forceChangePasswordNextLogin":false},     “immutableId”: “6SNZnFLe6jOI3n68hjO5zA==”

 }

 HTTP RESPONSE: 201 Created

 NOTE: in the above example, a password is required as part of the POST user creation call, but is not used because the User is using a Federated identity.

In this new API version, we have also exposed a new user property, userType.  This is a string value that can be used to allow tenants to classify the types of users within their organization.  For example, regular employees can be identified by userType =  “Member”,  and guest accounts associated with vendors, consultants or temporary workers, could be have userType = “Guest” .

 2. Support for User Licensing

This action was first available under a preview version (api-version=2013-04-10-preview) and is now officially supported in the “2013-11-08” release.  This method allows assignment and removal of a subscription for any provisioned user account. For example, here’s an initial license assignment of the Enterprise Office Sku, which contains SharePoint Online, Lync Online and the Exchange Online service plans.

POST 

https://graph.windows.net/contoso.com/users/adam@contoso.com/assignLicense?api-version=2013-11-08

HEADERS

Content-Type: application/json

Authorization: Bearer eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiIsIng1dCI6Ik5HVEZ2ZEstZnl0aEV1T….

BODY


 {  "addLicenses":[{"disabledPlans":[ ],"skuId":"6fd2c87f-b296-42f0-b197-1e91e994b900"}],  "removeLicenses":[ ]

 }

 HTTP RESPONSE:    200 OK

 

Here’s an example of updating a User’s license by disabling specific plans.  In this example, there are 2 disabledPlans (SharePointOnline and LyncOnline"), leaving only the Exchange Service Plan.

Select User License Assignment

POST

https://graph.windows.net/contoso.com/users/adam@contoso.com/assignLicense?api-version=2013-11-08

HEADERS

Content-Type: application/json

Authorization: Bearer eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiIsIng1dCI6Ik5HVEZ2ZEstZnl0aEV1T….

BODY


{   "addLicenses":[  { "disabledPlans":  [”5dbe027f-2339-4123-9542-606e4d348a72”,                                                            “0feaeb32-d00e-4d66-bd5a-43b5b83db82c” ], 

                             "skuId":"6fd2c87f-b296-42f0-b197-1e91e994b900"                             }  

                          ],   "removeLicenses":[ ]

 }

HTTP RESPONSE:   200 OK

 

Finally, here’s how to remove the license from the user.

Remove User License Preview

POST 

https://graph.windows.net/contoso.com/users/adam@contoso.com/assignLicense?api-version=2013-11-08

HEADERS

Content-Type: application/json

Authorization: Bearer eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiIsIng1dCI6Ik5HVEZ2ZEstZnl0aEV1T….

BODY


 {

  "addLicenses":[ ],  "removeLicenses":["6fd2c87f-b296-42f0-b197-1e91e994b900"]

 }

HTTP RESPONSE:   200 OK

 

How do you get the subscription Sku Id and the plan ids?  These can be read from the tenant object, by calling GET https://graph.windows.net/contoso.com/subscribedSkus
which will return the subscriptions available for the tenant – this includes the SkuId and servicePlans Id’s under the Sku. Availability of subscriptions can be calculated from the “consumedUnits” property and values
from “prepaidUnits” complex property, which includes counts of units that are “enabled”, “suspended” and in “warning” states.  You can view this using the https://GraphExplorer.cloudapp.net demo – select
“Use Demo Company”, and execute this query: https://graph.windows.net/GraphDir1.OnMicrosoft.com/subscribedSkus?api-version=2013-11-08

 3. Adding Group Members operation can now support multiple member objects in the same request.  

We have always allowed adding a single object to a group, but we now support multiple objects being added to a group in one call.  The example below adds two new users to a group.  NOTE: The maximum allowed number of links to add in a single POST/PATCH request should be kept to 20 or below.  Attempts to add a higher number of links can result in a failure response.

Update Group or Role membership

PATCH

https://Graph.windows.net/contoso.com/groups/02a8a087-a371-43f9-94df-cf0f654de307?api-version=2013-11-08

HEADERS

Content-Type: application/json

Authorization: Bearer eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiIsIng1dCI6Ik5HVEZ2ZEstZnl0aEV1T….

BODY


 {

   "members@odata.bind":

   [  

          "/contoso.com/users/09f8c01f-53cd-466f-9d2e-b7fb6a77b119",                 "/contoso.com/users/2ac58744-e872-49fa-bfb2-d0ff8c0d5750"

   ]

 }

HTTP RESPONSE:   204 No Content

 Note: Removing multiple members is not supported at this time.

 

4. Managing Group Owners  

How do you find a Group’s owner?  Easy - the following will return the Group's owner: GET https://Graph.windows.net/contoso.com/groups/02a8a087-a371-43f9-94df-cf0f654de307/owners?api-version=2013-11-08

The following will return the group object, and the owner objects in one call: https://Graph.windows.net/contoso.com/groups/02a8a087-a371-43f9-94df-cf0f654de307?$expand=owners?api-version=2013-11-08

And to assign an owner to a Group, the following POST operation can be executed:

Update a Group’s Owner

POST

https://Graph.windows.net/contoso.com/groups/02a8a087-a371-43f9-94df-cf0f654de307/$links/owners?api-version=2013-11-08

HEADERS

Content-Type: application/json

Authorization: Bearer eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiIsIng1dCI6Ik5HVEZ2ZEstZnl0aEV1T….

BODY


{

   "url":  "https://graph.windows.net/contoso.com/users/88478020-a5b2-4176-b720-838af8dee190"

}

RESPONSE: 204 No Content

 And with other links, you can also find out what objects are owned for a User: 

GET https://graph.windows.net/contoso.comt/users/adam@contoso.com/ownedObjects&api-version=2013-11-08

Or retrieve the user and the user's owned objects in one call: GET https://graph.windows.net/contoso.comt/users/adam\@contoso.com?$expand=ownedObjects&api-version=2013-11-08

5. Sorting lists of Groups by display name

We now allow your app to specify sorting by the Group’s display name property. For example: GET https://graph.windows.net/contoso.com/groups?$orderby=displayName?api-version=2013-11-8.  And in case you missed it in my previous blog post, you can specify sort order for user lists, by either the displayName or userPrincipalName property. 

6. Additional Differential Query features

Differential Queries can now return only updated properties and links – this allows faster processing and reduced payloads for Differential Query calls. This option is enabled by setting the header ocp-aad-dq-include-only-changed-properties to true as shown in this example.

 

GET

https://graph.windows.net/contoso.com/users?api-version=2013-11-08&deltaLink= furK18V1T….

HEADERS

ocp-aad-dq-include-only-changed-properties : true

Content-Type: application/json

Authorization: Bearer eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiIsIng1dCI6Ik5nl0aEV1T….

Response: 200 OK

For example if only the “displayName” property of user has changed.  The returned object would be similar to this:

{     

          "displayName" : "AnUpdatedDisplayName",

         "objectId" :  "c1bf5c59-7974-4aff-a59a-f8dfe9809b18",

         "objectType" :  "User",

          "odata.type" :  "Microsoft.WindowsAzure.ActiveDirectory.User"

},

Differential Sync Support to Sync from “now” - a special header can be specified, requesting to only get an up-to-date deltaToken, this token can be used in subsequent queries, which will
return only changes from “now”.  Here’s the example call:

GET

https://graph.windows.net/contoso.com/users?api-version=2013-11-08&deltaLink= smLYT8V1T…

HEADERS

ocp-aad-dq-include-only-delta-token: true

Content-Type: application/json

Authorization: Bearer eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiIsIng1dCI6Ik5nl0aEV1T….

Response: 200 OK

The response will contain the deltaLink, but will not have the changed object(s), similar to this:

{   …  "aad.deltaLink":https://graph.windows.net/contoso.com/users?deltaLink=MRa43......   }

We’ll dive into Differential Query calls in much more detail in the upcoming posts.

Give Use Feedback

We will be updating our sample applications to show some of the above mentioned features in the new version: https://msdn.microsoft.com/en-us/library/hh974459.aspx and in an upcoming post, we will include code snippets showing how to use these new capabilities.

Please let us know if the new features are useful, and let us know what other Api's will be useful for your scenarios.  Leave a comment or your questions on this Post.

Thanks, Edward

Azure Active Directory Team

Microsoft Corp

Comments

  • Anonymous
    November 25, 2013
    About "Provisioning Federated Users", you're killing me with your spelling, is it: "immutableId", "immutabelId" or "immudatableId"??

  • Anonymous
    November 25, 2013
    Apologies HansZ, it is corrected and should be "immutableId"

  • Anonymous
    November 26, 2013
    Brilliant! Thanks for this. I've been trying to use standard oData libraries against GraphAPI but I've discovered that there is no support for the standard oData paging mechanism via $top and $skip in api-version 2013-04-05. Is this available in this version?Sincerely,//Adam

  • Anonymous
    November 27, 2013
    Hi Adam, $top is available in the previous version (2013-04-05) and in this latest version (2013-11-08), however $skip is supported at this time. You can read my previous post about paging using $top and how to page forward and backwards.  Here's an example of paging for the first 999 results:graph.windows.net/.../users$top=999&api-version=2013-11-08let me know if you have more questions after reading our previous Post about paging.Thanks, Ed

  • Anonymous
    November 27, 2013
    i missed a "not" in my previous reply - I meant to write "... $skip is not supported at this time".-Ed

  • Anonymous
    December 10, 2013
    Excellent!... Now I can move off PowerSshell directly to Graph as the two major limitations have been addressed:Federated Users Licensing

  • Anonymous
    December 18, 2013
    The comment has been removed

  • Anonymous
    December 19, 2013
    Looks like you're executing this correctly - I just validated that I could update this on an existing user in my tenant.  how long of a value are you using for the immutableId property?

  • Anonymous
    December 24, 2013
    Thanks for the response.I can confirm that all works fine. That was some "strange" encoding issue on my side.

  • Anonymous
    January 13, 2014
    Great news - we've been waiting for license assignment and the ability to set ImmutableId.The only gap in support for us is the ability to update domain settings, moving them between managed and federated, and setting STS urls and signing keys. Will this be available on the Graph API and if so when?

  • Anonymous
    January 14, 2014
    The comment has been removed

  • Anonymous
    January 17, 2014
    Does the rest api support creating multiple users in one call? If yes can you post a sample payload?

  • Anonymous
    January 22, 2014
    Yes, we support batching - there are some current limits on the batching:batch size is currently limited to 5 operations (e.g. 5 GETs, 5 POSTs etc.)batch operations must be of the same type (e.g you can't have a GET, POST, PATCH, DELETE in the batch) I will follow-up and show the sample payload and response.

  • Anonymous
    January 27, 2014
    The comment has been removed

  • Anonymous
    January 28, 2014
    I'm using this solution in the institution where i work. But at this moment I'm having a problem to list all users. Only 100 records are displayed. I'm using this operation: msdn.microsoft.com/.../dn151678.aspxHow can i show ALL users?

  • Anonymous
    January 29, 2014
    Regarding the Error Creating User - if you receive 401 Unauthorized, then the only reason is the app doesn't have write permissions - can you do any other update operations, such as updating an existing user or deleting a user?   Or creating,updating,deleting a security group?BTW, when using client creds (appId and secret), the context of the logged on user doesn't matter - the logged on user is just a user (non-Admin), but the app has read/write permissions, then the app will have read/write permission when the user executes the app.Thanks, Ed

  • Anonymous
    January 29, 2014
    Answer to Ricardo's question about only 100 users being returned for this query:graph.windows.net/.../usersBy default, the page size is 100.  To specify a different page size, use $top - the maximum page size is 999 - for example: graph.windows.net/.../users$top=999Note, if there are more results beyond your page size, the response body will contain a property called odata.nextLink  For example (note, I truncated the skiptoken value to make this more readable):"odata.nextLink": "directoryObjects/$/Microsoft.WindowsAzure.ActiveDirectory.User?$skiptoken=X'44537074....000000'"To get the next page of results, your next query would use the $skiptoken value - for example:graph.windows.net/.../users$top=999&$skiptoken=X'44537074....000000'If you want to read more about paging (including how to page forward/backward), please review #3 on my post:blogs.msdn.com/.../enhancing-graph-api-queries-with-additional-odata-supported-queries.aspxThanks, Ed

  • Anonymous
    January 29, 2014
    Response to Rob Potter's question regarding domain management, and configuring managed and federation properties on the domains - you are correct, we don't have these API's today - it is something we are planning to add, so we have parity with capabilities available in Msonline PowerShell - stay tuned.Thanks, Ed

  • Anonymous
    January 30, 2014
    Answer to P.K's question about how to update the immutableId property - after the immutableId property is set on a user, and the user has a UPN that is using a federated domain, then the way to modify the immutableId is through a 3 step process:change the user's UPN to use a non-federated (i.e. managed) domain - for example: a user with UPN = Adam@contoso.com has an immutableId value set, and the domain, contoso.com is a federated domain.  We need to change the UPN to a managed domain (e.g. change UPN=Adam@contoso.onMicrosoft.com).Now update the immutableId value Now update the user's UPN back to the federated domain - set UPN=Adam@contosol.com these are the steps for modifying an existing immutableId property.  Also note: if you delete a user that has an immutableId value set, and you attempt to create or update a user to use the immutableId of the deleted user, your create/update attempt will fail with "..object already exists.."    This is because the object is in the soft-deleted state - to fix this, you will need to hard-delete the object, before attempting to re-use the immutableId on a new or existing object.

  • Anonymous
    March 10, 2014
    Is there an equivalent to Windows AD LogonUser operation in Windows Azure AD. This is to allow a user to silently login with his user ID and password to Azure AD to retrieve a JWT Token.

  • Anonymous
    March 31, 2014
    The comment has been removed

  • Anonymous
    March 31, 2014
    I've solved the problem. I've been referring to an MS implementation document, which put the verb required as PATCH. Send through the request with a POST verb and it works fine

  • Anonymous
    April 01, 2014
    How do I link the Offer Id provided in the MOSI PlaceOrder call to the subscriptions/subscribedSkus for that tenant?I know the MOSI SubscriptionId is an internal id to MOSI. However, we rely on the OfferId and send that across. Then, when querying GRAPH, I can get the SubscribedSkus....but this only gives me a list of servicePlans (inc. GUIDS); a SKU id (unique to the tenant); and an object Id.Given a tenant that has 2+ subscriptions (none of which to the same offerId), how do I link these to the offer Id?My question from above still stands also: how do i get the metadata for the 2013-11-08 api? I can make calls to this API but I can't retrieve the metadata (which is causing me problems with the immutableId not being present)?Appreciate your advice. Thanks

  • Anonymous
    April 05, 2014
    Edward,A little delayed, sorry! Not being able to use GraphAPI with standard OData libraries is a bit of a hassle, given the mechanism is similar, would it be possible to implement the $skip method?After all, its part of the standard and I'm a little miffed as to why a non-standard method was used, curious decision (:msdn.microsoft.com/.../ff478141.aspx//Adam

  • Anonymous
    July 23, 2014
    Whats the plan for updating these docs to include the new fields?msdn.microsoft.com/.../hh974483.aspxAlso how about something that describes permissible values for all known fields?

  • Anonymous
    July 23, 2014
    How does one set a value for thumbnailPhoto via the REST api? It says Edm.Stream, but does that mean I pass the bytes as a base64 encoded string?

  • Anonymous
    July 23, 2014
    What are the actual permissible values for 'userType'? The sentence below seems to imply the tenant can set it to any arbitrary string but that does not seem to be the case"In this new API version, we have also exposed a new user property, userType.  This is a string value that can be used to allow tenants to classify the types of users within their organization.  For example, regular employees can be identified by userType =  “Member”,  and guest accounts associated with vendors, consultants or temporary workers, could be have userType = “Guest” ."

  • Anonymous
    July 23, 2014
    For the "assignLicenses" featurea) I am doing the exact same thing as the example where I disable 2 service plans within a sku. This is accepted by the service with a 200b) I then do a GET of that user I just adjusted the licenses for. The service plans I disabled are not reflected in the AssignedPlans return element, NOR does the number of total AssignedPlans seem to reflect the changeWhy is this?

  • Anonymous
    September 15, 2014
    Is it possible to create a 'Microsoft Account' user with this version of the API?

  • Anonymous
    September 01, 2015
    there exist several complementary "relationships":  members|memberOf, owners|ownedObjects, manager|directReports ... if these were in an sql database, they might be represented in a simple relationship table.  what i'd like to be able to do is get that whole table returned to me, instead of having to pick a value in either column and get all the values it has in the "other column" in AAD, this would amount to a call that would return links with "one endpoint of the relationship, the relationship 'method', and the other endpoint of the relationship" is there anything i can do to mimic this result? as it stands, if i have N users and M groups, i have to do at least min(M,N) separate queries...  would like "one-stop-shopping" please!

  • Anonymous
    September 20, 2015
    Does "ocp-aad-dq-include-only-changed-properties" still work?  I've been trying to get it working with the 1.5 and 1.6 version apis and it always returns the entire object, not just the properties that were updated.

  • Anonymous
    November 23, 2015
    We are trying for optimization (minimizing the time required for aggregation) of aggregation process. Currently we are using pagination but it takes lots of time min 25hrs . We wanted to reduce it to 4-5 hrs. How to achieve that ?.  Is there any query to get all users in one call without using skiptoken? Or  is there any other way to do it ?

  • Anonymous
    January 04, 2016
    The comment has been removed