Sp-dev-docs: getToken() intermittently hangs and fails to resolve/reject

Created on 13 Nov 2019  ·  151Comments  ·  Source: SharePoint/sp-dev-docs

Category

  • [ ] Question
  • [ ] Typo
  • [x] Bug
  • [ ] Additional article idea

Expected or Desired Behavior

The promise returned by AadTokenProvider.getToken() should always resolve or reject. In other words, when a token can't be retrieved for whatever reason, I should get something back that I can catch.

Observed Behavior

getToken() is occasionally hanging - never resolving or rejecting so I can't catch an error or figure out what's happening. The .then() under getToken() just never runs and my web part stalls.

Steps to Reproduce

I'm trying to access a .NET Core Web API secured with AAD from my custom web part. I initially used the instructions found here but AadHttpClient.get() was occasionally stalling so I decided to get the token using AadTokenProvider.getToken() and manually add it to a HttpClient.get() but my issue didn't go away. I was however able to confirm that getToken() is where it hangs rather than an issue with the API. Here's my code:

this.context.aadTokenProviderFactory.getTokenProvider()
    .then((provider) => { 
        return provider.getToken('<Client ID for my API>', false) //THIS IS WHERE IT HANGS
            .then((token) => {
                this.context.httpClient
                    .get('https://www.example.com/api/myAPI/', AadHttpClient.configurations.v1, {
                        headers: [
                            ['accept', 'application/json'],
                            ['Authorization', 'Bearer ' + token]
                        ]
                    })
                    .then((res: HttpClientResponse): Promise<any> => {
                        return res.json();
                    })
                    .then(data => {
                        //process data
                    }, (err: any): void => {
                        this.context.statusRenderer.renderError(this.domElement, err);
                    });
            }, (rejection) => {
                this.context.statusRenderer.renderError(this.domElement, "Token request rejected. " + rejection);
            });
    })
    .catch((err) => {
        this.context.statusRenderer.renderError(this.domElement, "Failed to get token provider.");
    });

I noticed that it seems to hang after a period of inactivity like maybe it's failing to refresh a stale token or something. I'd expect the rejection code to execute but nothing beyond getToken() runs. But if I refesh the page a couple times, it starts working again.

This seems to be related to issue #914 reported on pnp/pnpjs.

Edit: I discovered that this is a lot easier to reproduce in Chrome. (I haven't seen it occur in IE and I've only seen it once or twice in Firefox although I can't seem to reproduce in FF at the moment. Edge gets the token but fails the API request for reasons I can't explain). In Chrome, it struggles every time it needs to grab a token. So, for example, it hangs the first time you load the page. If you refresh a few times, it starts working. Then if you leave the page open for a period of time (long enough for the token to expire) and refresh the page, it hangs again.

Edit 2: Per the conversation below, we can reproduce the issue when the custom web part is on the same page as a document library and a planner or events web part and it works fine when on a page by itself. There may be some sort of conflict with token retrieval/sharing between web parts.

auth spfx-general working-on-it bug-confirmed

Most helpful comment

Hi,

Just wanted to give some context regarding the issue and fix.

SPFx has been relying on ADAL.JS to fetch AAD tokens for 1st & 3rd party experiences. We found a race condition that was exposed by ADAL.JS's Authentication Context object being initialized on the same page multiple times. The race condition could not be patched, so a complete rewrite was done to avoid this & other potential pitfalls of using ADAL.JS. As you can imagine, this is a non trivial amount of code, so we want to give it as much bake time as possible to avoid creating a bad experience. The code should be rolling out slowly over the next couple of weeks.

This rewrite uses the Implicit Flow for acquiring AAD tokens, similar to ADAL.JS/MSAL.JS. We're working closely with the AAD team to move to MSAL 2.0, which we're expecting to have huge improvements in terms of performance and reliability.

All 151 comments

Thank you for reporting this issue. We will be triaging your incoming issue as soon as possible.

I spotted the following message in the console when it errored referring to mytenant.sharepoint.com/_forms/spfxsinglesignon.aspx:

Blocked script execution in '<URL>' because the document's frame is sandboxed and the 'allow-scripts' permission is not set.

@TheIronCheek said:

I noticed that it seems to hang after a period of inactivity

What do you mean by "period of inactivity?... you mean the page sitting open for a while? If so, how long is "period of inactivity"?

Long enough for the token to expire... a half hour maybe?

The problem seems to happen most consistently in Chrome. It looks like it happens whenever it needs a fresh token. So, the very first time the user hits the page, it fails. If you refresh the page a few times, it'll finally get a token. And then it fails again when that token expires and it tries to get a new token.

Any chance you have a sample project you can share (via public GH repo) to repro it? Will help speed up the repro to escalate the issue to engineering...

I'll throw something together for you.

_Sounds like_ after obtaining a token, SPFx just keeps using the same, but not handling the response if the token is expired. Have you inspected the request with Fiddler / network tab in the browser? When the request is made, I expect you'll see a response saying something like the token has expired... my theory is that this response isn't handled by the SPFx API and thus, they the promise is never resolving...

There are hundreds of requests being made on the page but watching the Network tab on a successful run, here's what I'm gleaning that looks pertinent:

  • It makes a GET request to https://login.microsoftonline.com/<tenant>/oauth2/authorize and the response is a 302 Found with Location header set to https://<tenant>.sharepoint.com/_forms/spfxsinglesignon.aspx#access_token=<token>.
  • Shortly after, it expectedly sends a GET request to https://<tenant>.sharepoint.com/_forms/spfxsinglesignon.aspx that responds with a 200 and sets FedAuth and rtFa cookies.
  • Shortly after that, it sends an OPTIONS request to my API and the API returns 204 No Content
  • It finally makes the GET request with the Authorization header set so that my API returns the actual data.

On a failing run, here's what I get:

  • The same GET request to https://login.microsoftonline.com/<tenant>/oauth2/authorize and the same 302 Found response that has Location set in the header to https://<tenant>.sharepoint.com/_forms/spfxsinglesignon.aspx#access_token=<token>.
  • The same GET request to https://<tenant>.sharepoint.com/_forms/spfxsinglesignon.aspx that responds with a 200 and sets FedAuth and rtFa cookies.
  • My API is never called.

Based on that, it looks like a token is being correctly retrieved since that Location header value in the response from https://login.microsoftonline.com has the access_token URL parameter set to a value. But for whatever reason, that token never makes it back to my web part so it can call my API.

Like I said, there are hundreds of requests that run here so it's tough to sift through and figure out what's relevant. If there's something specific I should look for, let me know.

I updated the OP with browser specific information.

I threw together a sample web part:

https://github.com/TheIronCheek/SampleWebPart

I have the exact same issue as you.

@andrewconnell
Do I need to open a new issue ? Or submit a msft support request to speed things up ?

@FlorianLabranche - I'm glad I'm not the only one. If you figure out what's going on, please - for the love of all that is holy - come back here and update me. I'll be sure to do the same. I have a ticket open with support too and I was told they're "escalating" the issue and that I'd for sure get a call back today. Still waiting.

Googling around today, I found this resolved issue from late October/early November.

It references the same message I get:

Blocked script execution in '<URL>' because the document's frame is sandboxed and the 'allow-scripts' permission is not set.

But in that situation, it only affected extensions and not web parts. Could my issue be tangentially related?

I am seeing simmilar issues. Might be something else, but maybe it helps to track down the issue...
For me this only happens if thre is an OOTB document libraray/list webpart on the page or a planner webpart. I think those ootb webparts are also getting a token for MS graph using the underlying adal infrastructure and interfering with the custom webparts. Looking at the tokens in the session storage of the browser, you can see that things get messed up.
Removing those ootb webparts and refreshing the page, i can get my token without any problems over and over again...

@OliverZeiser - I put my custom web part on a blank page with no other web parts to test a couple weeks ago and the problem didn't go away.

Although when I try it now, it seems to work fine on its own page...

Well now try to put a doc lib and planner webpart on the same page and try again a few times...

@OliverZeiser - I don't have the planner web part but I was able to reproduce the issue with a doc library and event web part (both of which are also on my main page).

I think we're onto something here.

@TheIronCheek I've checked multiple samples I use to demonstrate this and all seem to be working as expected. They are:

  • Use AadHttpClient to call an OOTB secured endpoint (MS Graph)
  • Use AadHttpClient to call a custom secured endpoint (REST API hosted with secured Azure Function)
  • Use MSGraphClient to call MSGraph

All of these use the same underlying infrastructure to obtain a token. I tested them individually & combined being the only web part on the page, with all of them on the page, and also with other OOTB web parts on the page (including the Document Library web part). I've been refreshing the pages and hitting them every other day and none of them are breaking. I'm trying, but I can't repro what you guys are saying.

I see two things in your code... one isn't terribly important, the other I suspect is your issue. I am not seeing the stalling out using the AadHttpClient.getClient()... I see you switched to AadTokenProvider.getToken()... that won't fix anything as you're now just doing the same thing the AadHttpClient does for you.

However, I see you're trying to reference your endpoint by the client ID... a GUID. That was supported in the dev previews, but that's not supported or how you're supposed to do it how. That value should be the endpoint of the service you are trying to reach. Look at the definition of the underlying getToken() method:

/**
 * Fetches the AAD OAuth2 token for a resource if the user that's currently logged in has
 * access to that resource.
 *
 * The OAuth2 token should not be cached by the caller since it is already cached by the method
 * itself.
 *
 * @param resourceEndpoint - the resource for which the token should be obtained
 * @param useCachedToken - Allows the developer to specify if cached tokens should be returned.
 * An example of a resourceEndpoint would be https://graph.microsoft.com
 * @returns A promise that will be fullfiled with the token or that will reject
 *          with an error message
 */
getToken(resourceEndpoint: string, useCachedToken?: boolean): Promise<string>;

Notice it's the endpoint... and the reference is the URL of the endpoint.

The AadHttpClient method says the same:

    /* Excluded from this release type: __constructor */
    /**
     * Returns an instance of the AadHttpClient that communicates with the current tenant's configurable
     * Service Principal.
     * @param resourceEndpoint - The target AAD application's resource endpoint.
     */
    getClient(resourceEndpoint: string): Promise<AadHttpClient>;

For reference, here's how I'm calling a custom service...

const NASA_APOLLO_MISSION_ENDPOINT_URI: string = 'https://voitanos-secure.azurewebsites.net';

export class MissionService {

  constructor(private aadHttpClientFactory: AadHttpClientFactory) { }

  public getMissions(): Promise<IMission[]> {
    return new Promise<IMission[]>((resolve, reject) => {
      this.aadHttpClientFactory
        .getClient(NASA_APOLLO_MISSION_ENDPOINT_URI)
        .then((client: AadHttpClient) => {
          const endpoint: string = `${NASA_APOLLO_MISSION_ENDPOINT_URI}/api/nasa-apollo-missions`;
          client.get(endpoint, AadHttpClient.configurations.v1)
            .then((rawResponse: HttpClientResponse) => {
              // verify successful response
              if (rawResponse.status === 200) {
                return rawResponse.json();
              } else {
                throw new Error('Error occurred when retrieving missions.');
              }
            })
            .then((jsonResponse: IMission[]) => {
              resolve(jsonResponse);
            })
            .catch((error) => {
              reject(error);
            });
        });
    });
  }
}

@OliverZeiser said:

I think those ootb webparts are also getting a token for MS graph using the underlying adal infrastructure and interfering with the custom webparts.

All of that stuff uses the SPO infrastructure to get a token which today still uses ADAL, including our custom stuff. The plan is to move to MSAL JS but ETA is unknown at this time. But that will be transparent to us as that's handled by the SPFx API.

@andrewconnell The same thing happens with MSGraphClient. And for me it looks like a timing issue and as such it is quite hard to reproduce. But here is an example what happens in the session storage:
When everything is working fine, the session storage for ADAL looks like this. This is with just one custom webpart requesting a graph token.
adal_single_ok

When adding the document library webpart to the page and hitting F5 a couple of times (after clearing the session storage) I'll eventually end up with this (note the invalid_state here):
adal_multiple_notok
As you can see there are not two tokens, but just one, the one from the document library webpart. My custom webpart failed when getting the token. This can be the other way around as well. Thats why I am guessing it is a timing issue when multiple components request a token more or less at the same time.

What it should look like and also does look like when I add one webpart first, wait until it has a token and then add another webpart to the page without clearing session storage is this:
adal_multiple_ok
Again this is a hint for me that it is probably a timing issue.

I know that this is very hard to reproduce. In my case it was easier to reproduce when adding an extension that requests a token than a second webpart. Again I am guessing it is due to the fact of the loading order for the components and since it is beeing related to a timing issue.
The more components you have on your page requesting differnt kinds of tokens, the easier it gets to reproduce it. Just make sure to clear the session storage all the time. Once you have a valid token things will be working fine for quite some time....

Yeah, the easiest way for me to reproduce it is to add my custom web part, a document library, and a 3rd OOTB web part like the Events web part and then open the page in an incognito window so the cookie isn't retained. A doc library and custom web part alone wasn't enough to trigger the issue.

@andrewconnell - When I switch the client ID to my API's endpoint in getToken(), my API returns a 401 Unauthorized message. I also get a 401 if I use AadHttpClient. Is it possible I have something configured incorrectly in Azure?

I can only confirm the above comments.

In my case it's an extension but it behaves the same. FYI, it's mainly used on Doc library pages.
As @OliverZeiser described it, in some case, SP get the Adal token for OOB SP calls but not for my API.

I also referenced my API with its client ID. Changing to the endpoint url give me this exception :
image

How can it work via Id (some times) but not via the endpoint ? If the app was granted consent, it should work in both case. Right ?

Joining the conversation - we're getting a somewhat similar issue above (#5003), using MSGraphClient. For us we have a dev and prod tenant, and this issue has appeared on both. For our dev tenant, it's only ever happened once for a few days across multiple accounts and then the issue stopped appearing since early November.

It's just started appearing for our prod after our last deployment (we've had multiple deployments for the last month and no reported issues). This is what my session storage looks like

Screen Shot 2019-12-10 at 11 42 46 pm

Has anyone been receiving this kind of error as well? I agree with @OliverZeiser that these issues do suggest that it's timing related, but I can't seem to reproduce the issue at all on our dev environment

@andrewconnell For me it is also not working with getClient().

image

Last log I see is "Almost there" then no news from Then or Catch.

@guillaume-kizilian That's expected. You aren't specifying anything in the getClient() method. That requires the URI of the resource you want the token for.

@FlorianLabranche your error that you show in your comment https://github.com/SharePoint/sp-dev-docs/issues/4892#issuecomment-563937497 indicates you are trying to access a resource that is secured with an AAD app in a different tenant. If this is a multitenant AAD app, you must first consent to it within your app PRIOR to requesting an access token. That will create the service principal in your tenant which will establish the "link" to the AAD app defined in the other tenant.

This is a configuration issue, rather a code issue, in your case.

More: https://docs.microsoft.com/en-us/sharepoint/dev/spfx/use-aadhttpclient-enterpriseapi-multitenant

@andrewconnell this is not the framework method, it is my override which explains why i don't need a parameter.

Here is my implementation :
image

Also i should still get an error and this is not where it stop but right after (I have the almost here log showing up)

@guillaume-kizilian said:

this is not the framework method, it is my override which explains why i don't need a parameter.

well that wasn't clear from your first comment... providing full context in an error report helps :)...

but from your most recent comment, you refer to this as the client ID. What is the value of that? If it's a GUID, that's not correct. It should be the URI of the resource, not a GUID.

@andrewconnell Yes, sorry :). It took sometimes but i've finally found out why. (Its hard when the process just hangs).
I forgot the webApiPermissionRequests of my app registration in package-solution.json. This was granted in Admin center for another SP Add-in, maybe this is why i got no error.

Not sure if it's linked to the original issue.

@andrewconnell I just noticed #3968, seems like it could be related? Specifically this comment look mores like the same error msg I was getting, but perhaps also related to this hanging issue?

@guillaume-kizilian said

I forgot the webApiPermissionRequests of my app registration in package-solution.json. This was granted in Admin center for another SP Add-in, maybe this is why i got no error.

In that case you would have received a 401 response.

@JasonPan My understanding was #3968 was an issue with the admin console and dealing with permission grant requests. While they fall in the same general "bucket" with AzureAD secured endpoints, getting a token is not related IMHO.

@andrewconnell you're right. it only worked for 15 minutes, I don't know why it did and why it stopped. On the other hand my other webpart using this system with exactly the same parameters works.

@andrewconnell - Why would I be getting a 401 after changing from the GUID to the endpoint URI?

@TheIronCheek Only if SPO has not consented permission to that resource. You can verify this by inspecting the access token with a tool such as https://jwt.io

@andrewconnell It's note a multi-tenant configuration in my case. But the exception was from a bad configuration indeed. The App ID URI is in format ap://[Application ID] and does not match the endpoint URL.
I still have a CORS issue caused by a bad Redirect URI (my guess). But the admin is out of office til mid-january.

I'll try a repro on another tenant to see if using App ID URI fixes the token issue.
I think it might does the job because the requests are handled differently when called with App ID URI or Application ID.

@FlorianLabranche said:

I'll try a repro on another tenant to see if using App ID URI fixes the token issue.

App ID (aka client ID) != App URI... I might be picky here, but that's an important distinction.

Using the app ID was supported in the dev preview, but it's not supported today. It might still work, but it's not the right way to do. The correct way to obtain an access token is to request it by the app's URI.

@andrewconnell said :

@FlorianLabranche said:

I'll try a repro on another tenant to see if using App ID URI fixes the token issue.

App ID (aka client ID) != App URI... I might be picky here, but that's an important distinction.

Using the app ID was supported in the dev preview, but it's not supported today. It might still work, but it's not the right way to do. The correct way to obtain an access token is to request it by the app's URI.

Does this mean that this doc is not up to date ? https://docs.microsoft.com/en-us/sharepoint/dev/spfx/use-aadhttpclient-enterpriseapi-multitenant#consume-enterprise-api-secured-with-azure-ad-from-the-sharepoint-framework
image

When i switch the guid to the app URI it just stop working on both extensions. Is there more directives to make it work ?

Thanks,

I am seeing the same issue at our tenant. A isolated SPFX webpart that worked fine till today (received first complaint today) now stops with the following message: "Token Renewal Failed - Description : Token renewal operation failed due to timeout". We are using the AADHttpClient to make a call to a Azure Function like this:
this.context.aadHttpClientFactory .getClient(this.applicationIDURI) .then((client: AadHttpClient): void => { client.get(${this.functionAppURL}, AadHttpClient.configurations.v1)

I am going to report this to premier support. Service is so bad lately...

@FlorianLabranche said:

I'll try a repro on another tenant to see if using App ID URI fixes the token issue.

App ID (aka client ID) != App URI... I might be picky here, but that's an important distinction.

Using the app ID was supported in the dev preview, but it's not supported today. It might still work, but it's not the right way to do. The correct way to obtain an access token is to request it by the app's URI.

Yes I get that. App ID URI as it's called on the app registration in AAD:
image

If the app registration is created when securing the API with AAD in Express (create) mode, it will match the API endpoint (...azurewebsites.net). That's where I get confused when following the doc because mine was manually created.

@guillaume-kizilian said:

Does this mean that this doc is not up to date ?

I'm double-checking with engineering on the App ID (GUID) vs. endpoint before I comment on this. My understanding as I've explained above is that you should use the App URI, not the GUID as the SDK docs state, and if that's correct I'll bug & update the doc. Stay tuned...

When i switch the guid to the app URI it just stop working on both extensions. Is there more directives to make it work ?

Can you give more detail than that? "It just stop working" isn't much to go on... error response, raw HTTP response when inspecting the request, etc...

@guillaume-kizilian following up on my last comment https://github.com/SharePoint/sp-dev-docs/issues/4892#issuecomment-567040079, confirmed with engineering the supported approach is to use the Azure AD app's URI.

Will bug & update the referenced doc...

This thread seems to mix up multiple issues now. The one desribed by the starter of this thread and also by me still exists and is not limited to AadHttpClient but can also be reproduced with MSGraphClient. For me it happens especially if I add an ApplicationCustomizer to the top that is makeing calls to the graph and combine it with OOTB webparts on the page like calendar, planner and document library webpart.
I can reproduce it on multiple tenants and with multiple solutions. So the issue still exists and can't be due to a wrong Azure AD URI

@andrewconnell - I'm looking at the decoded access token and I don't see anything jumping out to make me think it's invalid.

  • the "aud" value is set to my API's endpoint URI
  • the "appid" value is the Client ID for the "SharePoint Online Client Extensibility Web Application Principal"
  • the "family_name" and other user-specific values are correctly showing my personal details
  • the "scp" value is "access_as_user user_impersonation"

When I use the Client ID for getToken() instead of the API's endpoint URI, the token is basically identical, just with the "aud" value set to the my API's Client ID.

Where do I go from here?

@andrewconnell - This documentation uses the Client ID as well.

@TheIronCheek Can you share the token? If necessary, just remove the parts that would make it useful (like the last section of GUIDs or the part of the tenant in the UPN)...

@TheIronCheek said:

This documentation uses the Client ID as well.

Thanks for calling that out. Just bugged it #5069 as the other doc is already bugged and on my backlog to fix. I've confirmed with engineering that ClientID is 100% not supported.

No problem. I should be able to get that to you once I'm back in the office Thursday morning.

@andrewconnell - Here's my decoded token when I use the API's endpoint URI. My API returns a 401 Unauthorized message.

Capture

Hello, I'm following this issue because it seems to be related with the #5003 in SPFx calling Graph API. @andrewconnell In that case, do we follow this issue or is it a different one?

In my case, the problem happens when calling the Graph API from an SPFx webpart inside a tab from Teams. The Graph call is returning the error "Token renewal operation failed due to timeout" even after deleting the session and local storage. However, this same webpart is correctly working inside SharePoint, it's just in Teams where it fails.

The problem appeared on November and it suddenly started to work again after a few days until the past 23th of December, when it started to give again the error and has not recovered from it.

Thank you in advance!

Is there an update already?

@andrewconnell - I got the API working. In my API's Startup.cs, I was specifying the expected audience as the Client ID which is why it was returning a 401 when using the endpoint URI. I fixed that but the bug is still present.

In short, updating my code to use the endpoint URI instead of the client ID did not fix the bug I'm reporting.

It still hangs whenever it tries to get a new token and the <promise> never returns. If I refresh the page several times, I'll eventually get the <promise> to return and my web part works as expected.

I think @OliverZeiser may have nailed the problem when he mentioned the ADAL infrastructure being a problem. I'm getting the same invalid_state error he's getting.

invalid state

I've been reading about ADAL JS limitations when used with the SharePoint Framework. @andrewconnell - Are these limitations present when using AadTokenProvider as well?

I think those (most of them...) limitations should not be there when working with the authentication flow provided by SPFx like with AadHttpClient. That is one reason why all that was done by MS and why we don't have to use ADAL JS ourselves.
But I am also waiting for a statement from Microsoft here. I would love to know at least if this is a known bug and if there is work beeing done. Maybe @patmill or someone else from the team can provide a quick update, so we know if there is anything we need to do on our side besides waiting ;)

@OliverZeiser - That was kind of the vibe I got from the docs too, that not having to deal with token issues was the whole reason for using AadHttpClient instead of a manual ADAL JS implementation. But here we are with token issues so maybe there's something we're missing.

I'm also curious if anyone with the issue is using domain isolation. I am not - mainly because the web part stopped working completely when I set "isDomainIsolated": true (which is an issue I could bring up if I needed to...) but also because messing with responsiveness issues from loading content in an iframe is a pain. I'm only using user_impersonation for my API and User.Read from Graph which isn't a huge deal for us in terms of what escapes if another web part sniffs my token.

But the reason I ask is that I'm wondering if loading this web part in an iframe would shield it from whatever conflict is happening between it and the OOTB web parts...

_Not ignoring this thread, it just heated up when many (including me) took time off at the end of the year. And now, trying to dig out from the backlog. I'll catch up, but @TheIronCheek's last comment stuck out..._

Isolated web parts get their own Azure AD app so you need to grant the permission(s) request(s) to that app. If all you did was change the setting and redeploy, then that's expected it wouldn't work until the permission was granted.

@andrewconnell - I probably messed this up early in my testing process. I remember early on when I was making the web part that a strange app had been created in AAD (named after my app) along with the SharePoint Online Client Extensibility Web Application Principal and SharePoint Online Client Extensibility Web Application Principal Helper app registrations. When things weren't working I tried deleting all the permissions and app registrations so I could start over.

Now, when I turn on domain isolation and redeploy, I don't get a new app registration in Azure. So I'm kind of stuck with no way to approve anything.

Hi @TheIronCheek

I was able to repro your issue following the steps outlined in your original post. I've identified the issue (race condition with Document Library component trying to do Auth) and I'm working on a fix now. Will update the thread when

  1. The issue is fixed
  2. The fix has been rolled out 100% PROD.

Sorry about the delay

That is good news. Thank you for the update! We are looking forward for this fix. Hopefully this fix is not just for the document library component, because the same thing happens with the planner webpart or group calendar webpart (and maybe other components as well...)

@OliverZeiser The fix is in the underlying token acquisition code, so it should handle any issues with both 1st and 3rd party components 😉

Thanks for your help @lahuey and @andrewconnell !

@lahuey Great news !

@OliverZeiser The fix is in the underlying token acquisition code, so it should handle any issues with both 1st and 3rd party components 😉

On my side, the issue is between an extension and a document library page itself (Forms/AllItems.aspx). I hope the inner "doc lib component" uses the same underlying code as well !

Should it fix the spfxsinglesignon.aspx errors ?
2020-01-09 17_00_14-Sans titre - paint net v4 2 8

We have the exact same spfxsinglesignon.aspx errors when using SPFx Teams tabs with browser. However, no issues with Teams desktop client.

Hi @TheIronCheek

I was able to repro your issue following the steps outlined in your original post. I've identified the issue (race condition with Document Library component trying to do Auth) and I'm working on a fix now. Will update the thread when

  1. The issue is fixed
  2. The fix has been rolled out 100% PROD.

Sorry about the delay

@lahuey do you have an ETA for this fix?

This issue still exists for us when "User Consent" is disabled in Azure Active Directory.
image

When set to No, you cannot even create a direct website tab link to a SharePoint site:
image
image
image

The tab is added, but doesn't load correctly:
image
And the console is showing x-frame-options errors:
image

This also means that AadHttpClient auth in a Teams app breaks, as it also relies on Microsoft Teams being able to render the SPFx app in the iFrame, but as it's hosted in an iFrame, it runs into the same x-frame-options issue:
image

So it looks like when this AAD setting is disabled, there are stricter x-frame-option settings applied to SharePoint which means they no longer execute correctly in a Team Tab. (Microsoft are going to be setting this setting to No by default on all tenants shortly, so this is going to be a huge impact for everyone using SPFx apps in Teams).

@rayhogan Can you (temporaily) disable their browser cache, and try again. That should resolve the issue you're seeing.

@guillaume-kizilian These errors are from SPO running an experiment with MSAL.js. They are safe to ignore and will not affect your component's ability to fetch tokens. We're working with the MSAL team to address these "ignorable" errors.

@v-pajorg About a month, but hopefully less.

@FlorianLabranche yes, it's the same component behind the scenes. We need to update our calling pattern to ADAL.js (used behind the scenes) in order to avoid this race condition.

@lahuey - Disabling the browser cache has no impact. I've tested every possible scenario for the past week and the only thing that gets it working again is changing this setting back to yes:
image

When it is set to yes, I can see through Fiddler and the browser's Network tab that there are no x-frame-options on the SharePoint call, but when it is set to No*, SharePoint has an x-frame-options header of 'SameOrigin' which prevents it being called within the Teams iFrame.

The issue for us is that Microsoft has recommended that this setting is set to No, and is pushing a change to all tenants to set this to No by default.

For us this issue manifests when loading an SPFx tab in Teams as described in #5116. The root cause seems to be that the SharePoint token acquisition logic relies on loading spfxsinglesignon.aspx from SharePoint within a Teams application iframe. This fails because spfxsinglesignon.aspx usually (not always) returns X-Frame-Options = SAMEORIGIN header, and as a result the iframe loading is blocked by browser policy and token acquisition fails.

An example flow that fails:

In addition the result of spfxsinglesignon.aspx is also cached, so once you get a response with X-FRAME-OPTIONS: SAMEORIGIN that same response is used for subsequent token acquisition flows resulting in the same error.

You can verify that the issue is resolved by temporarily (!) installing the following Google Chrome extension, which causes the browser to ignore X-Frame headers and load the iframe contents regardless of the header.
https://chrome.google.com/webstore/detail/ignore-x-frame-headers/gleekbfjekiniecknbkamfmkohkpodhe

What I find strange is that spfxsinglesignon.aspx does not consistently return the X-FRAME-OPTIONS header, and never returns it when you send the Cache-Control=no-cache header. This is why disabling browser caching (e.g. Google Chrome dev toolbar -> network -> disable cache) fixes the problem.

Running the following PowerShell:

1..50|%{invoke-webrequest "https://microsoft.sharepoint.com/_forms/spfxsinglesignon.aspx"|select @{n="Cache-Control";e={$_.headers."Cache-Control"}},@{n="X-Frame-Options";e={$_.headers."X-Frame-Options"}}}

results in:

Cache-Control X-Frame-Options
------------- ---------------
public        SAMEORIGIN
public        SAMEORIGIN
public        SAMEORIGIN
public        SAMEORIGIN
public        SAMEORIGIN
public        SAMEORIGIN
public        SAMEORIGIN
public        SAMEORIGIN
public        SAMEORIGIN
public        SAMEORIGIN
public        SAMEORIGIN
public        SAMEORIGIN
public        SAMEORIGIN
public        SAMEORIGIN
public        SAMEORIGIN
public        SAMEORIGIN
public
public
public
public
public
public
public
public        SAMEORIGIN
public
public        SAMEORIGIN
public
public
public
public
public
public        SAMEORIGIN
public
public
public
public
public
public
public
public
public
public
public
public
public        SAMEORIGIN
public
public
public        SAMEORIGIN
public
public        SAMEORIGIN

The same when disabling cache:

1..50|%{invoke-webrequest "https://microsoft.sharepoint.com/_forms/spfxsinglesignon.aspx" -headers @{"Cache-Control"="no-cache"}|select @{n="Cache-Control";e={$_.headers."Cache-Control"}},@{n="X-Frame-Options";e={$_.headers."X-Frame-Options"}}}

results in:

Cache-Control X-Frame-Options
------------- ---------------
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public
public

Actually, disabling cache does cause it work:
image

But this isn't a solution as our customers access to dev tools is blocked by policy.

@maskati @rayhogan
I'm also concerned about what your saying but could you track the issue you're describing in another ticket as it's not directly related to the original post and leave this thread to track down update about the getToken() issue and fix ?

I'm pretty sure it will also help the dev team to track your issue more efficiently.

I would say #5116 could be the correct issue, however it was closed it as a duplicate of this.

@maskati / @FlorianLabranche - Yes I had an issue opened but it was closed as this ticket was considered to be a duplicate, but I also think that, while the errors are the same, the root cause is different so it could potentially warrant a separate ticket.

Ok.
As you said, your token renewal issue seems related to the AAD settings and X-FRAME option. But it could also be related to the one on this thread.

Let's see what the gurus say !

@rayhogan I am seeing this exact same issue except my "user consent" option is enabled. This was working in December and stopped working in January if that helps narrow down what might have changed. Also my code base hasnt changed since November.

I can also confirm disabling the cache resolves this issue but isn't a scalable solution.

@rayhogan @bealsao could you email me the tenant url and sprequestguid from the "same origin" aspx page request? I haven't been able to repro this issue, but a look into the logs would really help!

My email is [email protected]

@lahuey It's my dev tenant so Im happy to give you a login and let you see the problem in action if you'd prefer. I'll send you an email with the Tenant URL and if you want a login to reproduce the behavior reply to my email and let me know.

@lahuey you can reproduce this by calling spfxsinglesignon.aspx in any tenant (the page does not require authentication). See my earlier message

Here you can see that without the Cache-Control: nocache request header, 9/10 responses returned the X-Frame-Options response header, and by disabling cache no responses contained the header:

image

I'm having the same issue and debug outputs with domain isolated webparts as a SharePoint app page. Weirdly it works on Edge, but not on Chrome.

@maskati thank you for detailed response. It's quite strange that this ASPX page is only returning the correct response sometimes. I'll update the thread when I have more details/proposed fix.

We opened a premium support ticket with MS. They have since acknowledged the issue and have supposedly rolled out a fix to all tenants. I have confirmed it now works on our environments.

Can confirm its working for me.

I can confirm the same as @rayhogan. We also created a support ticket. They said it was due to a invalid refresh token. It is now fixed in our tenant as well.

I'm still getting my original issue where my custom web part won't run when on the same page as other OOTB web parts.

The fix that you all are talking about is unrelated to the token issue @lahuey said could take a month or so to fix, correct?

@TheIronCheek correct.

The Cache-Control issue has been resolved already, but the race condition issue is still open.
There was a couple other higher priority items that needed to be addressed before I could start fix this issue.

@lahuey Regarding the issue which I had reported #5164 - I can be confirmed that the issue Refused to display 'https://myorg-app.sharepoint.com/_forms/spfxsinglesignon.aspx... ... ...' in a frame because it set 'X-Frame-Options' to 'sameorigin'. no more exist in the browser. However, still facing an issue on MS Team Desktop client.

@lahuey - Just touching base on this again since it's been a little over a month. Do we have a new ETA for the fix here? Thanks!

@TheIronCheek The fix is now in review. Should roll out slowly over the next ~3 weeks.

Apologies for the wait. The fix required multiple changes on both the server and client. We're expecting to see an improvement in the performance and reliability of the token provider APIs after the fix rolls out.

Thank you for patience :)

@lahuey - Any word on the current status? I seem to still be getting this error today. Is there a particular version I need to update to for this fix?

Still not fully functional on my tests (depending on the tenant), I guess this is why the issue is still open.

@lahuey any eta, news, tests on your side ?

Thanks.

@dvrax @guillaume-kizilian

We’re still working through some issues that prevent us from deploying the upgraded token provider APIs. We want to ensure that the upgraded API resolves all of the open issues without causing regression.

@lahuey do we have any ETA for race condition issue in token provider.
We are recently using it in SPFX extension using Bot framework and as pointed out after inactivity of around 1 hour (that's when token expires and ideally should fetch refresh token) it is stuck in resolving
MicrosoftTeams-image

@lahuey I have started seeing this issue on our tenant from the last 2 weeks. We were analyzing this issue and found it was recommended to use Azure AD App URI instead of App AD ( getToken('') ). Initially, I thought this has been happening because I was using App ID, but I tried replacing the app ID with App URI. But still, it has happened. Do I need to create a separate MS ticket for our tenants to get it resolved? Also, is there any workaround on this?

In our tenant, this issue only presents itself when loading the page with the webpart directly (Browser URL, Link, or Bookmark) and only on the first load. I can hit browser refresh and it will work perfectly. Once it is in this failing state all requests to the API will hang.

const CLIENTID = 'api://xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx';
// Token Hangs
const provider = await context.aadTokenProviderFactory.getTokenProvider();
const token = await provider.getToken(CLIENTID);
// Fiddler shows a request for the token, but never makes the request to the API and the promise hangs
const client = await context.aadHttpClientFactory.getClient(CLIENTID);
var response = await client.fetch(`${APIPATH}/contacts`, AadHttpClient.configurations.v1, options);

@lahuey do we have any ETA for race condition issue in token provider.
We are recently using it in SPFX extension using Bot framework and as pointed out after inactivity of around 1 hour (that's when token expires and ideally should fetch refresh token) it is stuck in resolving
MicrosoftTeams-image

I have the same problem

Also on a few customers from Premier support

We have started facing this issue on our tenant from the past 2 days. The spfx webpart using MsGraphClient throws "Token renewal operation failed" issue on first load in chrome browser. On refresh the issue does not occur and data is returned. Is this something we needs to be fixed from our end or your end.

@lahuey , @andrewconnell
Token Renewal issue has started to appear. Reiterating the behavior from the 1st post here,
"it hangs the first time you load the page. If you refresh a few times, it starts working. Then if you leave the page open for a period of time (long enough for the token to expire) and refresh the page, it hangs again"

Kindly provide response. It is impacting clients

Just debugged the session in Chrome and Firefox and in the end the following message occurs:

Chrome:
A cookie associated with a cross-site resource at https://webshell.suite.office.com/ was set without the SameSite attribute. It has been blocked, as Chrome now only delivers cookies with cross-site requests if they are set with SameSite=None and Secure. You can review cookies in developer tools under Application>Storage>Cookies and see more details at https://www.chromestatus.com/feature/5088147346030592 and https://www.chromestatus.com/feature/5633521622188032.

Firefox:
Content Security Policy: De instellingen van de pagina blokkeerden het laden van een bron op inline (‘script-src’).
It's in Dutch, but it says the page setting blocked the loading of a inline script.

In Firefox this could be resolved by changing one flag: security.csp.enable
But that is no real fix. On some tenants it's nearly impossible to get a token to use at the moment..

I'm also seeing issues with MSGraphClient not fulfilling requests in an SPFX ApplicationCustomizer. It eventually does work when you keep refreshing, but there's no warnings or errors in console. This may be related as it sounds symptomatically similar (and I believe MSGraphClient uses aadTokenProviderFactory under the hood).

I see the auth loop happening to login.microsoftonline.com requesting a token for https://graph.microsoft.com which loops back round to singlesignon.aspx, but the client's call into .api() never completes.

Also: This never occurs when debugging the solution via ?loadSpfx=true..., it works every time when doing that.

EDIT: My issue is down to a custom web part that I've got that uses this auth loop. It's interfering with the OOTB MSGraphClient in SPFX. Without my webpart on the page, the graph bits work fine.

EDIT EDIT: My issue might not be relevant after all, it appears I wasn't using the AadHttpClientFactory correctly in my solution, so the token retrieval was interfering. The instructions here helped me.

I agree this might be a timing issue. When I tested it on the page where no other web part exists other than my custom SPFx, it worked well. However, if I add other web parts document library or any other web part which also tries to obtain a token, it fails.
I start seeing this issue on my tenant from the last three weeks when we were approaching a go-live date soon. So I had to find out some solution/workaround on this.
A) Very first thing, getToken() method promise hangs and it hangs all its successive promises. So I thought instead of Promise let’s try with $.Deferred, but that was not adequate and there was no way to check if Promises being hanged. So I thought let’s add some waiting time for few seconds until getToken() promise completed. E.g. if we have not received resolved/failed from a promise for 5 seconds which is I believe sufficient time to find out if promise hangs (You may try by varying it depending upon your requirement) and that we considered as promise ‘timeout’ or hanged. So we can try one more time again to obtain a token, and if this ‘timeout’ as well. Then we can conclude page is loading first time and getToken() promise being hanged. So this is sufficient to take next action B)
For the above mention workaround, I made a few changes in my TOKEN class as below. This may be helpful to you to try it out.

class TOKEN {

    public static getMyToken =  (ctx:WebPartContext, useCached: boolean = true): Promise<any> => {    
        return ctx.aadTokenProviderFactory.getTokenProvider()            
            .then( (tP: AadTokenProvider): Promise<string> => {
                return tP.getToken( "api://blablablablablablablabla" ); // For SPFx 1.9 -> return tP.getToken( “api://blablablablablablablabla”, useCached );
            })
            .then((token:string):string => {    
                return token;
            })
            .catch((error:any) => {
                console.log("Token cannot obtained, Error details-"+error);
                return null;
            });
    }

    public static getT = ( ctx: WebPartContext, cachedToken: boolean = true ) => {
        var dfd = $.Deferred();
        console.log('after deferred');
      // Wait for 5 seconds to check if promise hanged
        TOKEN.promiseTimeout(5000 , TOKEN.getMyToken ( ctx, cachedToken ) )
        .then( res => { console.log('deferred resolved'); dfd.resolve( res); })
        .catch( err => { console.log('deferred rejected'); dfd.reject( err ); });        
        return dfd.promise();
    }

    public static delay( ms: number) { return new Promise( resolve => setTimeout(resolve, ms)); }

    public static getAADToken = async ( ctx: WebPartContext, cachedToken: boolean = true ): Promise<any> => {
        var dfd = $.Deferred();

            console.log('Trying-1st');
            TOKEN.getT( ctx, cachedToken ).done( tkn => { dfd.resolve( tkn ); })
            .fail( async error1 => {
                console.log('error1-'+error1);
                await TOKEN.delay(500);
                console.log('Trying-2nd');
                TOKEN.getT( ctx, cachedToken ).done( tkn => { dfd.resolve( tkn ); })
                .fail( async error2 => {
                    console.log('error2-'+error2);                    
                    dfd.reject(error2);
                });
            });

        return dfd.promise();      
    }

    public static promiseTimeout = (ms: number, prm: Promise<any>): Promise<any> =>  {
        let timeout = new Promise((resolve, reject) => {
            let id = setTimeout(() => {
                clearTimeout(id);
                reject('timeout');
            }, ms);
        });

        return Promise.race([
            prm, timeout
        ]);
    }
}

Here is code to call the getAADToken method from the front end.

TOKEN.getAADToken ( ctx, true )
        .then( function ( token ) {
            console.log('Captured Token'); // Get toke without issue onwards from 2nd time refresh
            callCustomApi( token );

        console.log('Call check access function');

    })
    .catch( err => {
        console.log('token error-'+err); // timeout error as getToken hangs (First time page load)
        if( err == 'timeout') {
            console.log('session'+sessionStorage.getItem("adal.access.token.key"+window.location.protocol+"//"+window.location.hostname));
            if(sessionStorage.getItem("adal.access.token.key"+window.location.protocol+"//"+window.location.hostname))
            {
                console.log('Read value form session storage');
                var token = sessionStorage.getItem("adal.access.token.key"+window.location.protocol+"//"+window.location.hostname);
                callCustomApi( token );
            }
        }
    });

B) Above option just check if your promise is being failed. But we have to take the next action to get the token and pass it to a custom API, but this wasn’t working as our first promise hangs it hangs all successive promises until you refresh the page.
Unexpectedly, I saw in session it returns another token which may be being requested from either doc library or any other web part. So I thought to use this token to call my API.

Fortunately, I have custom code that validates token in code behind when a custom API being called. So, I made the enhancement in my token validation code which validates this generated token as well (so it accepts and validates both types of tokens) and returns a response and getting data back on first-time page load. Following are the console log I get when the page loads first time.

image

This is just a workaround I am using until we get a concrete solution.

Is there an ETA on solution?
We opened a premier ticket because we have it on about 5 different tenants as of last week ....

We are experiencing similar issues at multiple tenants/clients with both AadHttpClient and the MSGraphClient. Both clients don't seem to get a token. No call to the Graph or our custom API is made. We tried to optimize the size of our package but this did not fix it. The only token that is in the session storage is the one for SharePoint itself. After refreshing the page, everything works fine.

We began experiencing this issue approximately 2 weeks ago in a critical business webpart. After a lot of testing we created a new webpart with the sole functionality of retrieving a token from a tokenprovider, and then logging it to the browser console.

public render(): void {
    this.context.aadTokenProviderFactory.getTokenProvider().then(provider => {
      provider.getToken('MY GUID').then(token => {
        console.log(token);
      })
    });
  }

That webpart also failed.

The same webpart retrieved and printed the token as soon as the page was refreshed.

We are experiencing similar issues at multiple tenants with AadHttpClient

We're experiencing the same thing on multiple tenants, using the PnPjs graph client, this happens even with the SPFx graph sample

@andrewconnell and @VesaJuvonen could you please have a look at this issue? It is affecting multiple tenants and a large set of our customers. I strongly believe this issue should get priority from the product team.

Ping from our side. All our web parts on multiple customers are failing, using the Graph token now. Opened a premier ticket with microsoft.
Fidller shows no token requests. Confirm this issue when combined with the document library web part for example, on one page.

Ping from our side. All our web parts on multiple customers are failing, using the Graph token now. Opened a premier ticket with microsoft.
Fidller shows no token requests. Confirm this issue when combined with the document library web part for example, on one page.

Are you sure this is the same issue? I do see the token requests in the network tab. Problem on our side is there is only a 302 found code and no actual 200 response. So there is no actual token in the session storage for the Graph API and our custom API until I refresh the page.

Ping from our side. All our web parts on multiple customers are failing, using the Graph token now. Opened a premier ticket with microsoft.
Fidller shows no token requests. Confirm this issue when combined with the document library web part for example, on one page.

Are you sure this is the same issue? I do see the token requests in the network tab. Problem on our side is there is only a 302 found code and no actual 200 response. So there is no actual token in the session storage for the Graph API and our custom API until I refresh the page.

Hello adrichema, I can confirm it's the same issue. I worked on this together with Renevdo. What we see is that most of the time, getToken() freezes, and when it freezes we don't see the request to graph. Once it worked it keeps working, and we do see requests, until we delete all storage and cookies for that site in Chrome, or maybe after some time. It seems like a race condition somewhere or a somehow cached promise that has already been fired (Made that mistake myself once)

It might be unrelated, but when I debugged this issue far into sp-pages-assembly.js, that chome message about samesite popped up like an exception. And I can confirm this only seems to happen when other webparts, like a document library are on the page.

It looks like the issue is occurring less. Does anybody agree?

It looks like the issue is occurring less. Does anybody agree?

We're unable to reproduce the issue anymore, so I would agree, it would seem there has been an update can anyone at MS confirm this?

Nope.. Unfortunately the issue still occurs on our customer tenants. We got a reply from Microsoft support and they simply pointed me to this issue. Microsoft is aware of this problem, but doesn't give us an ETA. Hope they fix this very soon, because all graphs based SPFx widgets are broken at the moment and our customers think it's out product that causes this.

It looks like the issue is occurring less. Does anybody agree?

We're unable to reproduce the issue anymore, so I would agree, it would seem there has been an update can anyone at MS confirm this?

Did you try deleting all cookies, local- and session storage for that site? That immediately reproduces the issue on our tenants.

It looks like the issue is occurring less. Does anybody agree?

We're unable to reproduce the issue anymore, so I would agree, it would seem there has been an update can anyone at MS confirm this?

Did you try deleting all cookies, local- and session storage for that site? That immediately reproduces the issue on our tenants.

Seemingly still works, did a [CTRL] + [SHIFT] + [DEL] and deleted everything from the past hour no difference.

Using Chrome v. 83.0.4103.116 64-bit on W10 version 1909 build 18363.900

Only a single webpart on the page (sample PnP Graph webpart that lists your groups)

It looks like the issue is occurring less. Does anybody agree?

We're unable to reproduce the issue anymore, so I would agree, it would seem there has been an update can anyone at MS confirm this?

Did you try deleting all cookies, local- and session storage for that site? That immediately reproduces the issue on our tenants.

Yes we tried. After deleting session storage we can reproduce the issue, but only if there is a document library webpart on the page. If we remove the webpart then the issue does not occur. when removing the session storage.

It looks like the issue is occurring less. Does anybody agree?

We're unable to reproduce the issue anymore, so I would agree, it would seem there has been an update can anyone at MS confirm this?

Did you try deleting all cookies, local- and session storage for that site? That immediately reproduces the issue on our tenants.

Yes we tried. After deleting session storage we can reproduce the issue, but only if there is a document library webpart on the page. If we remove the webpart then the issue does not occur. when removing the session storage.

We're able to reproduce the issue by adding a document library webpart to the page.

EDIT: I can't get it to work at all if there is a document library webpart, I'm not sure if these issues are related or not.

I've created a repo for my failing webpart in case anyone wants to see if they spot anything wrong.
https://github.com/Tanddant/GraphProblemSample-

I can replicate the issue too.

Graph calls work fine on a page with just my custom webpart. If I add a document library web part, delete all cookies and storage data, it fails on every load.

Document library kills my web part.

Is there an ETA on solution?
We opened a premier ticket because we have it on about 5 different tenants as of last week ....

@inconscienceAdmin Have you had a response from MS on this?

I've had some customers tell me this is apparently no longer an issue but I can still reproduce on my dev tenant, and other customers still see it. Are MS rolling something out?

Is there an ETA on solution?
We opened a premier ticket because we have it on about 5 different tenants as of last week ....

@inconscienceAdmin Have you had a response from MS on this?

I've had some customers tell me this is apparently no longer an issue but I can still reproduce on my dev tenant, and other customers still see it. Are MS rolling something out?

@RyanHealy Yes, we had a response from microsoft. There was indeed an issue with ADAL, but a fix would be ready and rolled out by the end the week.
I noticed that indeed the issue is no longer appearing on a couple of tenants, so I assume this has been rolled out or is being rolled out as we speak. :)

I'm still seeing the document library webpart killing my graph webpart on our dev environment (Targeted release).

Anyone with different results?

Here same results. But Microsoft mailed us with an ETA for at least an update:
Next update by: Monday, July 20, 2020, at 10:00 PM UTC

@TazzyMan, did you get an update from Microsoft?

Hello adrichema, No, unfortunately I didn't get any mail yet and the problem still exists on our customer's tenant.
I'll just give a few days. Don't know what to do the speed the process up (premier ticket didn't help), so we'll just have to wait I'm afraid.

I have a few clients who would like an official acknowledgement of this issue from MS, the last official activity on this post was on January the 8th.

Is it possible to get an official Microsoft update instead of relying on support tickets when it is not just a single tenant issue, I've tried to get MS to acknowledge the issue in a support ticket, but they simply refer me back to this thread, but my client would like something more recent (given that they only started seeing the issue recently)

I have a few clients who would like an official acknowledgement of this issue from MS, the last official activity on this post was on January the 8th.

Is it possible to get an official Microsoft update instead of relying on support tickets when it is not just a single tenant issue, I've tried to get MS to acknowledge the issue in a support ticket, but they simply refer me back to this thread, but my client would like something more recent (given that they only started seeing the issue recently)

Tuesday, July 21, 2020 5:44 AM GMT
Hello Daniel,
The product group has checked in some code that should fix the issue, but we are waiting on the ETA for the fix to roll out to production tenants.

I will keep you posted.

Best regards,

Westley Hall
SharePoint Developer Support

So you all know. Got an e-mail from Microsoft this morning and this is the most important part:

Current status:
Our fix has been validated in our internal testing environment. We're currently reviewing multiple deployment methods to mitigate impact in the affected environments due to the complex nature of the fix, and will provide an ETA on deployment once we've confirmed the most viable solution to proceed.

Next update by:
Friday, July 24, 2020, at 10:00 PM UTC

Hi,

Just wanted to give some context regarding the issue and fix.

SPFx has been relying on ADAL.JS to fetch AAD tokens for 1st & 3rd party experiences. We found a race condition that was exposed by ADAL.JS's Authentication Context object being initialized on the same page multiple times. The race condition could not be patched, so a complete rewrite was done to avoid this & other potential pitfalls of using ADAL.JS. As you can imagine, this is a non trivial amount of code, so we want to give it as much bake time as possible to avoid creating a bad experience. The code should be rolling out slowly over the next couple of weeks.

This rewrite uses the Implicit Flow for acquiring AAD tokens, similar to ADAL.JS/MSAL.JS. We're working closely with the AAD team to move to MSAL 2.0, which we're expecting to have huge improvements in terms of performance and reliability.

Hello, are there any updates on this issue?

We are experiencing issues with AadHttpClient in our SPFx web parts that consume Azure AD-Secured APIs. The first time user accesses a page with an SPFx web part that consumes an Azure AD-Secured API it works fine. But after a period of inactivity like 30 mins, if the user tries to access the same page or another page with another SPFx web part that makes an Azure AD-Secured API call the request fails with a 401 unauthorized error. Based on our troubleshooting, the AadHttpClient is still using an expired access token from a previous session. The older access token gets cached and there is no way to get out of this. Closing the browser or clearing browser cache doesn't resolve this issue. This is the same behavior in new Edge and Chrome.

SharePoint Online REST APIs are working fine. We have a few pages that have multiple web parts and the web parts consuming SPO APIs are working fine but the ones consuming Azure AD-Secured APIs are failing.

We are currently experiencing production outages due to this issue. A critical case was opened with Microsoft yesterday but seems like we are having very hard time trying to get to the product team. This is absolutely frustrating as our hands are totally tied and we are not getting much help from Microsoft.

@lahuey Is there an easy way to see if the update is rolled out to us? I can see that spfxsinglesignon.aspx is still referencing adal.js on our tenant (assuming this is indeed the utility page that handles SPFX redirectUri and places tokens into session storage).

We are also experiencing this issue! After 30 minutes of inactivity all calls to the Graph and our own Azure AD protected API are failing with 401 errors. CRTL + F5 does not help! Only closing the browser and restart seems to fix the issue. This is very inconvenient.

We are seeing the same behaviour as @adrichema and @jkondakindi are describing. Any updates on this issue?

Hi all,
We got an e-mail from Microsoft that indicates the problem should be fixed now.
Tested yesterday on the clients environment and seems to work now.

As the OP, it appears that the issue has been resolved almost everywhere for me.

I'm still getting issues in the old non-Chromium Edge, though. My web part doesn't work at all there. It just hangs.

@lahuey @andrewconnell - Anything word from MS about whether the issue is actually resolved, if the fix didn't include support for the older Edge, or if I'm just having an additional non-related problem?

@TheIronCheek I can't say... I don't have any additional insight. Might take a look at this: https://github.com/SharePoint/sp-dev-docs/issues/6135#issuecomment-681001868

Worth noting non-Chromium Edge is on death row...

We are facing this issue where token gets expired after 60 minutes approx. and then we have to close the browser to get the refreshed token. We are using single app part page with SPFX. So there is no other OOB web part on the page. Any help?

Is anyone still having the original issue? I haven't run into it since before @TazzyMan posted his response from MS saying it's fixed. I was hoping for something official from @andrewconnell saying MS had indeed addressed the issue but assuming no one else is having the issue, I'll go ahead and close this.

@asim-bashir-confiz - It sounds like a different issue. Our issue happens only when a custom web part is on the same page as an OOB web part.

@TheIronCheek Andrew closed a bug that described the issue that @asim-bashir-confiz has (and I also have) as a duplicate, that's why I'm still watching this thread

Didn't get any complaints from our customer anymore. Either they gave up or it's fixed now.

We are still facing the above issue. it's not resolved yet in our tenant. Do let us know if you need any more information about the same.

@umarokeeffetrade @OmAlim @asim-bashir-confiz

See: https://github.com/SharePoint/sp-dev-docs/issues/4892#issuecomment-682105898

We are facing the same problem that @umarokeeffetrade @asim-bashir-confiz are referring to.

Since we don't have an ETA from MSFT, is there a workaround that we could use (till MSFT deploys the fix on our production tenant)? I wonder if there is a way to silently request a new token before the existing one is about to expire? Not ideal but atleast it will reduce the annoyance for our users who, right now have to close the browser tab in order to access the application once the token expires.

it's really weird that this is not yet resolved after all those months;

we have implemented custom events in app insights (exclusively just to measure annoyance of users) and on our tenant ~10% of 'data loads' in our components ends with 401 unauthorized error (from graph api - MSGraphClientFactory and custom api hosted on azure - AadHttpClient);

as a workaround we added sessionStorage.clear() and a request to the user to refresh the page in error messages;

I'm wondering how it looks in internal MS logs - I bet that majority of 401's is a result of this issue here and not 'real' unauthorized access;

anyway I hope this will be fixed soon...

is there any updates from MSFT of the fix deployed on all tenants. How it can be verified whether the fix is available on a tenant?
Anyone still facing race issue even after the fix available?

Was this issue solved ? We still see the same behavior.

It seems like we have a similar issue. Was it deployed to all tenants?
How can I check whether our tenant has this fix?

Token retrieval timeout
Error: Token retrieval timeout at https://spoprod-a.akamaihd.net/files/sp-client/chunk.spoImplicit_none_0381f45b4fba0f3b19df.js:1:3485

on and on today...

AFAIK the currently deployed patch (using MSAL 1.x) should not be having an issue regarding expired tokens which are not resolved properly (which was the case with the old/previous ADAL version).

In all of our clients i see the MSAL implementation is active (check if you see there are any msal.* entries in your sessionStorage). If you still see adal.* entries, the old ADAL implementation is still active for your tenant.

You can still face concurrency issue's when you have multiple webparts each requesting tokens for the same resource scope (besides it is not efficient). I have solved this by creating my own library (based on MSAL v2).

Indeed on our tenant we see only ADAL in session storage - not a single MSAL.
What can we do from your side ?

Well i think you have the following options:

  • Wait for Microsoft to deploy the MSAL version (1.4.x) to your tenant.
  • Built your own authentication library (use MSAL v2 for this if you want to do this)
  • Depending on if you still experience the ADAL expiring token issue, you can implement some sort of workaround by monitoring the tokens and remove them if they are about to expire. ADAL will automatically acquire news tokens for you. In the past, i have implementend a simple AutoInvalidateAdalTokens webpart which does this job (with a configurable interval) to ensure the tokens are allways valid (and not expired).
Was this page helpful?
0 / 5 - 0 ratings