0

My authentication service has these behavior subjects

public isLoggedIn$: BehaviorSubject<boolean> = new BehaviorSubject<boolean>(false);
public isLoaded$: BehaviorSubject<boolean> = new BehaviorSubject<boolean>(false);

When a user is already logged into the site, it takes a second for the authentication service to load and set the isLoggedIn$ to true. Is there a way to wait for the next value of a behavior subject to change before returning? I imagine it to look something like this

export class AuthGuard implements CanActivate {
    private authLoaded = false;
    private loggedIn = false;

    constructor(
        private authService: AuthService,
        private router: Router,
        private toast: ToastrService,
    ) {
        authService.isLoggedIn$.subscribe(loggedIn => {
            this.loggedIn = loggedIn;
        });

        authService.isLoaded$.subscribe(authLoaded => {
            this.authLoaded = authLoaded;
        });
    }

    canActivate(
        next: ActivatedRouteSnapshot,
        state: RouterStateSnapshot,
    ): Observable<boolean> | boolean {
        if (this.authLoaded === false) {
            this.authService.isLoggedIn$.subscribe..awaitForNextValue..(loggedIn => {
                this.loggedIn = loggedIn;
                return of(this.loggedIn);
            });
        } else {
            return this.loggedIn;
        }
    }
}
user1222324562
  • 965
  • 2
  • 9
  • 24
  • 1
    maybe you can check this: https://stackoverflow.com/questions/38425461/angular2-canactivate-calling-async-function – katwhocodes Jul 05 '19 at 19:56

1 Answers1

1

In the CanActivate docs, check the return types. If you return a boolean instead of the others (Observable<boolean | UrlTree> | Promise<boolean | UrlTree> | boolean | UrlTree), it will execute synchronously instead of asynchronously.

Additionally, guards will execute in the order they are in the guards array for that route.

dockleryxk
  • 407
  • 2
  • 11