1
votes

What is the proper way to sign out of an Angular application using Firebase Authentication and Firestore?

I'm able to sign in with Google authentication and to sign out, but there are difficulties. My goal is that when a user clicks the logout button:

  • They are logged out of the site and their Google account.
  • All of their Firestore data is cleared away.

Instead of this, I find that on mobile Chrome (for some reason), their Google login is not cleared away, which means it is impossible to switch user accounts without clearing the browser data. (EDIT: I have been able to get this behavior, by deleting the user from the auth object; code below.)

I also frequently get the following error — fairly regularly, though I can't predict when it will happen. (It happens in development and when the app is deployed.) I suspect this is related to the signout problem, because I can fix the error by deleting the IndexedDB objects.

screenshot of INTERNAL ASSERTION FAILED: Unexpected state

My signout code comes from this answer and this video. I call a method in my database adapter service (dbService below). (The router navigation is an attempt to clear the browser.)

this.dbService.signOut().then( (value) => {
  this.router.navigate(['/' ])
    .then( (value) => { 
      window.location.reload();
     });
} );

this.dbService.signOut() is show below. (dbService is a service.)

  signOut() : Promise<void> {
    // unsubscribe to ensure no memory leaks
    this.productAdapter.destroy();
    this.customersAdapter.destroy();
    this.customerTypesAdapter.destroy();
    this.employeesAdapter.destroy();
    this.transactionsAdapter.destroy();
    this.preordersAdapter.destroy();
    this.giftsAdapter.destroy();
    this.nonconsumablesAdapter.destroy();

    return this.afAuth.signOut()
    .then( () => {
      /// this successfully signs the user out of his/her google account
      this.afAuth.currentUser.then( (user : firebase.User | null) => {
          user?.delete();
      } );
      this.clearLocalData();
    });
   }

At various times as well I have experimented with the lines below, to try to clear the data.

localStorage.clear();
await window.indexedDB.deleteDatabase("firebaseLocalStorageDb");
await window.indexedDB.deleteDatabase("firestore/[DEFAULT]/XXXXXXX/main");
/// as well, deleting all the cookies

I've got my dependencies below. The only thing that isn't straight out of the Firebase documentation is firebase-angular.

  "dependencies": {
    "@angular/animations": "^9.1.9",
    "@angular/cdk": "^9.2.4",
    "@angular/common": "^9.1.9",
    "@angular/compiler": "^9.1.9",
    "@angular/core": "^9.1.9",
    "@angular/fire": "^6.0.0",
    "@angular/forms": "^9.1.9",
    "@angular/localize": "^9.1.9",
    "@angular/material": "^9.2.4",
    "@angular/material-moment-adapter": "^9.2.4",
    "@angular/platform-browser": "^9.1.9",
    "@angular/platform-browser-dynamic": "^9.1.9",
    "@angular/router": "^9.1.9",
    "@angular/service-worker": "^9.1.9",
    "@google-cloud/firestore": "^3.8.4",
    "firebase": "^7.14.6",
    "firebase-admin": "^8.12.1",
    "firebase-functions": "^3.6.2",
    "firebaseui": "^4.5.0",
    "firebaseui-angular": "^5.0.0",
    "hammerjs": "^2.0.8",
    "moment": "^2.26.0",
    "rxjs": "~6.5.5",
    "tslib": "^1.13.0",
    "zone.js": "~0.10.2"
  },

EDIT: The error goes away if I don't enable disk persistence. But I need disk persistence for my application.

I tried changing the FirebaseUI configuration to signInFlow: 'redirect',. That's probably a better option anyway (as this is for a mobile app), but it didn't solve this problem.

1
Can you post the code which actually has line this.afAuth.signOut()madteapot

1 Answers

0
votes

In the end I've removed firebaseui-angular from my project, and am just using Firebase's JS API for authentication. It's quite possible I was using firebaseui-angular incorrectly, but I wasn't able to figure that out. Using the plain Firebase JS API seems to have solved my problem.