A community member has associated this post with a similar question:
Getting "The remote server returned an error:(401) Unauthorized" even after getting access Token

Only moderators can edit this content.

The remote server returned an error: (401) Unauthorized even after using Access Token from Azure for Sahrepoint Site

Apoorv 1 Reputation point
2021-06-16T07:11:14.313+00:00

I was able to get the access token for Sharepoint Tenant, from the App registered in AAD through Code 'AcquireTokenForClient'. But when I created Client Context for Site inside the Sharepoint tenant, using ""Bearer " + accessToken" I got following error on "Context.ExecuteQuery()"

The remote server returned an error: (401) Unauthorized

Under API permission I have Sharepoint >> Manage, Read & Write

Not sure what is wrong here. Here's my code, please help:

        static async Task  UploadFileToSharePoint(string SiteUrl, string DocLibrary, string ClientSubFolder, string FileName)
        {
            try
            {
                System.Net.ServicePointManager.SecurityProtocol = (SecurityProtocolType)(0xc0 | 0x300 | 0xc00);


                string clientId = "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"; 
                string certThumprint = "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"; 

                var scopes = new string[] { "https://<tenant>.sharepoint.com/.default" };

                string tenantId = "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX";
                var accessToken = await GetApplicationAuthenticatedClient(clientId, certThumprint, scopes, tenantId);

                using (ClientContext CContext = GetClientContextWithAccessToken(SiteUrl, accessToken))
                {

                    FileCreationInformation newFile = new FileCreationInformation();
                    byte[] FileContent = System.IO.File.ReadAllBytes(FileName);
                    newFile.ContentStream = new MemoryStream(FileContent);
                    newFile.Url = Path.GetFileName(FileName);

                    Web web = CContext.Web;
                    List DocumentLibrary = web.Lists.GetByTitle(DocLibrary);
                    CContext.Load(DocumentLibrary);
                    CContext.ExecuteQuery();
                    Folder Clientfolder =null;
                    if (ClientSubFolder == "")
                    {
                        Clientfolder = DocumentLibrary.RootFolder;
                    }
                    else 
                    {
                        Clientfolder = DocumentLibrary.RootFolder.Folders.Add(ClientSubFolder);
                        Clientfolder.Update();
                    }
                    Microsoft.SharePoint.Client.File uploadFile = Clientfolder.Files.Add(newFile);
                    CContext.Load(uploadFile);
                    CContext.ExecuteQuery();
                    Console.ForegroundColor = ConsoleColor.Green;
                    Console.WriteLine("The File has been uploaded" + Environment.NewLine + "FileUrl -->" + SiteUrl + "/" + DocLibrary + "/" + ClientSubFolder + "/" + Path.GetFileName(FileName));
                }

            }
            catch (Exception exp)
            {
                Console.ForegroundColor = ConsoleColor.Red;
                Console.WriteLine(exp.Message + Environment.NewLine + exp.StackTrace);
                MessageBox.Show(exp.Message + " (Ref: 401)");
            }
            finally
            {
                Console.ReadLine();
            }
        }

        internal static async Task<string> GetApplicationAuthenticatedClient(string clientId, string certThumprint, string[] scopes, string tenantId)
        {
            X509Certificate2 certificate = GetAppOnlyCertificate(certThumprint);
            IConfidentialClientApplication clientApp = ConfidentialClientApplicationBuilder
                                            .Create(clientId)
                                            .WithCertificate(certificate)
                                            .WithTenantId(tenantId)
                                            .Build();

            AuthenticationResult authResult = await clientApp.AcquireTokenForClient(scopes).ExecuteAsync();
            string accessToken = authResult.AccessToken;
            return accessToken;
        }

        public static ClientContext GetClientContextWithAccessToken(string targetUrl, string accessToken)
        {
            ClientContext clientContext = new ClientContext(targetUrl);
            clientContext.ExecutingWebRequest +=
                delegate (object oSender, WebRequestEventArgs webRequestEventArgs)
                {
                    webRequestEventArgs.WebRequestExecutor.RequestHeaders["Authorization"] =
                        "Bearer " + accessToken;
                };
            return clientContext;
        }

        private static X509Certificate2 GetAppOnlyCertificate(string thumbPrint)
        {
            X509Certificate2 appOnlyCertificate = null;
            X509Store certStore = new X509Store(StoreName.My, StoreLocation.CurrentUser);
            certStore.Open(OpenFlags.ReadOnly);
            X509Certificate2Collection certCollection = certStore.Certificates.Find(X509FindType.FindByThumbprint, thumbPrint, false);
            if (certCollection.Count > 0)
            {
                appOnlyCertificate = certCollection[0];
            }
            certStore.Close();
            return appOnlyCertificate;

        }
SharePoint
SharePoint
A group of Microsoft Products and technologies used for sharing and managing content, knowledge, and applications.
9,565 questions
SharePoint Server Development
SharePoint Server Development
SharePoint Server: A family of Microsoft on-premises document management and storage systems.Development: The process of researching, productizing, and refining new or existing technologies.
1,569 questions
Microsoft Entra ID
Microsoft Entra ID
A Microsoft Entra identity service that provides identity management and access control capabilities. Replaces Azure Active Directory.
19,389 questions
0 comments No comments
{count} votes

1 answer

Sort by: Most helpful
  1. Siva-kumar-selvaraj 15,546 Reputation points
    2021-06-17T18:34:51.9+00:00

    Hello @Apoorv ,

    Thanks for reaching out.

    Could you please try decode access token from https://jwt.ms and take a look at "aud" value from decoded token, it should looks like below screenshot also make in token you see appropriate permission mentioned.
    106741-image.png

    If all looks good from Azure AD token aspect then this would required expertise from SharePoint aspect. Therefore, adding SharePoint tags part of this thread to get SharePoint expertise.

    Please find below threads related this issue.

    https://stackoverflow.com/questions/47306898/sharepoint-online-web-api-bearer-error-401
    https://stackoverflow.com/questions/65685274/sharepoint-app-only-authentication-throwing-the-remote-server-returned-an-error
    https://stackoverflow.com/questions/55791232/call-sharepoint-online-with-same-aad-token

    Hope this helps.

    ------
    Please "Accept the answer" if the information helped you. This will help us and others in the community as well.

    0 comments No comments