target: SharePoint Online, Azure AD
code environment: Azure Functions, .Net Core


My goal is to ensure a user to a SharePoint site programmatically (via CSOM) and this user is a Security Group.

abstract workflow

  1. create a new security group in Azure AD --> take group-id, e.g. "asd-123-asd-123-asd"
  2. create a new O365 group with certain site alias "mySite" and wait for site to be created
  3. retry 30x or until success: add security group as user to the site with EnsureUser function


let my tenant-id be "qwe-345-qwe-345-qwe"

using Microsoft.SharePoint.Client

... SomeClass ... SomeFunction with try/catch and retry logic...
    using (ClientContext clientContext = new ClientContext("https://myDomain.sharepoint.com/sites/mySite"))

        clientContext.ExecutingWebRequest += (s, e) =>
            e.WebRequestExecutor.RequestHeaders["Authorization"] = "Bearer " + spoAppToken;

        Web site = clientContext.Web;
        loginName = "c:0t.c|qwe-345-qwe-345-qwe|asd-123-asd-123-asd";
        User spUser = site.EnsureUser(loginName);
        clientContext.Load(spUser, u => u.Id);
        clientContext.ExecuteQueryRetry(4, 500);

        log.LogInformation($"Ensured SharePoint site user!");
        return spUser.Id;


When it fails it throws a Microsoft.SharePoint.Client.ServerException with "Der angegebene Benutzer c:0t.c|qwe-345-qwe-345-qwe|asd-123-asd-123-asd wurde nicht gefunden." which is german for "The specified user c:0t.c|qwe-345-qwe-345-qwe|asd-123-asd-123-asd could not be found".


It always fails on the first try with this code. When I add this group via SharePoint UI it works instantly.

The only solution seems to reruning this code multiple times until SharePoint finds the user. I've set the rety limit to 30 retries with 10 seconds delay after each retry. In my testing environment this limit was never exceeded but yesterday it exceeded the limit in one of our production environments.

This behavior seems unpredictable and for some time I thought I was using the framework wrong, but since the login name is correct and it is working after some retries the code seems to be right.

I could imagine that there has to happen a certain sync process so that SharePoint knows what groups and users are available in the Active Directory, but why is it working instantly using the UI on the SharePoint site? And should't "EnsureUser" do exactly that?


Is there a better/more reliable way for ensuring security groups as users on SharePoint sites using CSOM, or another API? Or, am I doing something wrong?

Running 30+ retries doesn't seem to be the right approach.

  • Perhaps a stupid question, but what is your ultimate end goal? I.e., would Azure Access Packages be more appropriate?
    – user6024
    Jan 29, 2021 at 17:45
  • My goal is to ensure (or "add") a user to a SharePoint site programmatically. What makes this special is that this user is a security group. Sorry, but I can not see how Azure Access Packages could help with that, as this has nothing to with the libraries I am using right now.
    – theofred
    Jan 31, 2021 at 8:11

1 Answer 1


You don't have to use tenant-id for the loginName, just use tenant will be work.


You could try this:

loginName = "c:0t.c|tenant|asd-123-asd-123-asd";
  • I found that it makes no difference, whether I use the tenant id or the string "tenant". Both variants behave the same way.
    – theofred
    Feb 1, 2021 at 8:59

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.