Skip to content

[Auth Guard - BUG] canActivate auth guard causes blank screen after cache clear with multiple tabs opens. #3691

Open

Description

@DanielNovaesDias

If using the canActivate auth guard (with spread syntax), If you have more than 1 tab open of the same app, and then you clear the cache by using the browser in one of the tabs, and try to refresh, it causes a blank screen, which resolves after you close the other open tab.

steps to reproduce:

versions:
"@angular/common": "^20.3.0",
"@angular/compiler": "^20.3.0",
"@angular/core": "^20.3.0",
"@angular/fire": "^20.0.1",
"@angular/forms": "^20.3.0",
"@angular/platform-browser": "^20.3.0",
"@angular/router": "^20.3.0",
"rxjs": "~7.8.0",
"tslib": "^2.3.0",
"zone.js": "~0.15.0"

steps to reproduce:

  1. Create new project
  2. install angular fire
  3. setup authentication and firebase project
  4. utilize the ...canActivate auth guard like below.
  5. open two tabs of the same page.
  6. in one of them, clear the cache (by using the button close to the url in chrome for ex)
  7. refresh
  8. blank screen.
  9. verify that if you close the second tab, then the first one loads correctly.
const redirectTeste1 = () => redirectLoggedInTo('test2');
const redirectTeste2 = () => redirectUnauthorizedTo('teste1');

export const routes: Routes = [
  { path: '', redirectTo: 'teste1', pathMatch: 'full' },

  {
    path: 'teste1',
    component: Test1,
    ...canActivate(redirectTeste1),
  },

  {
    path: 'teste2',
    component: Test2,
    ...canActivate(redirectTeste2),
  },
];

lmk if this is somehow a user error, but with such a barebones configuration I think is a legitimate bug.

Activity

  1. changed the title [-][BUG] canActivate auth guard causes blank screen after cache clear with multiple tabs opens.[/-] [+][Auth Guard - BUG] canActivate auth guard causes blank screen after cache clear with multiple tabs opens.[/+] on Feb 14, 2026
  2. armando-navarro commented on Nov 5, 2026

    @armando-navarro
    Collaborator

    Hi @DanielNovaesDias, thanks for the clear steps, and sorry this sat without an answer for so long. I could reproduce the hang, but not through the exact button you described, so I may be missing a detail of your setup.

    What I found

    • The hang is not in the guard. canActivate waits for the first value from Firebase Auth's onIdTokenChanged, and in the stuck tab that callback never fires, so the route never resolves and nothing renders.

      • The guard code is the same in 20.0.1 and on main, so no AngularFire version changes this.
    • The wait is inside Firebase Auth's startup.

      • With the default persistence it opens the IndexedDB database firebaseLocalStorageDb, and that open request waits forever when a delete of the same database is pending and another tab still holds a connection to it.
      • Nothing throws and nothing is logged. Closing the other tab lets the delete finish, which is the recovery you saw.
    • I reproduced it with the plain Firebase SDK and no AngularFire at all, on Firebase 11.8.1 and 11.10.0 (the oldest and the newest 11.x that @angular/fire 20 accepts), 12.18.0 and 13.1.0, and then the blank page itself in an Angular 20.3 app with @angular/fire 20.1.1 and the routes from your report.

      • The trigger in my runs is an indexedDB.deleteDatabase('firebaseLocalStorageDb') call in one tab while another tab is open.
    • Deleting the site's data from the page-info bubble in Chrome 157 did not reproduce it for me: the reloaded tab started normally. So I would like to understand which action you took.

    Two questions

    • Which Chrome version were you on, and which exact control did you use to clear the data (the page-info bubble, DevTools, the clear browsing data dialog, or something in the app)?

    • Were you signed in at the time, and does the hang still happen on the current Chrome?

    Where the fix belongs

    I have filed the blocked-delete hang on the Firebase SDK tracker as firebase/firebase-js-sdk#10590, with a two-tab page that reproduces it. The fix belongs there (a timeout on the startup check, or closing the connection when a delete is requested), so I am keeping this issue open until that lands.

    A workaround you can use now

    Creating Auth with local storage persistence instead of IndexedDB avoids the hang entirely, because startup never touches that database:

    import { getApp } from '@angular/fire/app';
    import { browserLocalPersistence, browserPopupRedirectResolver, initializeAuth, provideAuth } from '@angular/fire/auth';
    
    provideAuth(() => initializeAuth(getApp(), {
      persistence: browserLocalPersistence,
      popupRedirectResolver: browserPopupRedirectResolver,
    }))

    Three things to know about it:

    • The session is then kept in localStorage rather than IndexedDB.

    • A user who is currently signed in through IndexedDB is signed out once after the switch, since the SDK reads only the persistence it is given.

    • The resolver line keeps signInWithPopup and signInWithRedirect working, which getAuth() sets up for you and initializeAuth does not.

    I ran this in an Angular 20.3 app with @angular/fire 20.1.1 and your routes: with getAuth() the reloaded tab stays blank until the other tab closes, and with the snippet above it renders right away. If any of this points somewhere I have missed, I will dig back in.

  3. added
    comp: authAuthentication (src/auth).
    comp: auth-guardRouter auth guards (src/auth-guard).
    needs: more infoWaiting on the reporter for repro, versions, or detail.
    triaged: keep-openTriaged and intentionally kept open; exempt from any future stale process.
    type: bugDefect: expected behavior doesn't happen.
    on Nov 5, 2026
  4. armando-navarro commented on Nov 6, 2026

    @armando-navarro
    Collaborator

    A quick update. The Firebase team closed firebase/firebase-js-sdk#10590 as a duplicate of firebase/firebase-js-sdk#10540, which hangs in the same startup check through a different trigger. Its fix is in PR firebase/firebase-js-sdk#10553, which is still in review, so no Firebase release includes the fix yet.

    I built that PR locally and ran the same two-tab test against it, and the reloaded tab no longer hangs. Auth finished starting after about 5 seconds while the other tab was still open, in each of three runs.

    Until a release includes the fix, the browserLocalPersistence workaround in my earlier comment still works, and I'll keep this issue open. My two questions above still stand if you get a chance to answer them.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    comp: authAuthentication (src/auth).comp: auth-guardRouter auth guards (src/auth-guard).needs: more infoWaiting on the reporter for repro, versions, or detail.triaged: keep-openTriaged and intentionally kept open; exempt from any future stale process.type: bugDefect: expected behavior doesn't happen.version: current (v17+)Targets the current modular API (v17+).

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions