Angular - loginWithRedirect() not working

Hello! I am having trouble with properly integrating Auth0 into my Angular application.

I followed this tutorial to integrate Auth0 into my Angular application, the one from the Auth0 docs. I made sure that I followed all of the instructions correctly.

Signing up for an account works, but after signing up, I cannot log in. When executing loginWithRedirect() after creating an account, it does not launch the login window. It instead takes me back to my app with isAuthenticated$ set to false. When I look at the client authentication history, I see this:

It says that I had a successful login, but the Identity Provider is N/A. Furthermore, when I look at the success details, Connection is also N/A and “connection_id” is blank. I do not know if this has anything to do with my problem.

I have looked through the Auth0 docs and searched on Google for answers as to why isAuthenticated$ always returns false after calling loginWithRedirect(). I have noticed that many people have encountered and solved this problem with many different solutions, but none of those solutions fix my problem.

It is worth noting, however, that if I execute loginWithPopup() with specific checks that I found online beforehand, it authenticates fine with isAuthenticated$ set to true. I provided my code at the end of this post with how loginWithPopup() successfully works for my app.

I do not understand why loginWithRedirect() always returns isAuthenticated$ as false no matter what solutions I find online. I have provided my code below.

I am currently using version 2.0.1 of auth0/auth0-angular.

environment.ts (I have MY_DOMAIN, MY_CLIENTID and MY_AUDIENCE filled in correctly in my app)

export const environment = {
  production: false,
  auth0: {
    domain: 'MY_DOMAIN',
    clientId: 'MY_CLIENTID',
    redirect_uri: window.location.origin,
    audience: 'MY_AUDIENCE'
  }
};

app.module.ts

import { AuthModule } from '@auth0/auth0-angular';
import { environment as env } from '../environments/environment';
// ...
@NgModule({
// ...
    AuthModule.forRoot({
      domain: env.auth0.domain,
      clientId: env.auth0.clientId,
      authorizationParams: {
        redirect_uri: env.auth0.redirect_uri,
        audience: env.auth0.audience
      },
      cacheLocation: 'localstorage'
    }),
// ...
})

login.component.html

<div class="container login-container">

  <div class="row">
    <h1 align="center">
      TITLE
    </h1>
  </div>

  <div class="row justify-content-center">
    <button mat-flat-button
            class="login-button"
            type="button"
            (click)="attemptLogin()">
      Login or Sign Up (Auth0)
    </button>
  </div>

  <div class="row justify-content-center">
    <button mat-flat-button
            class="login-button"
            type="button"
            (click)="logout()">
      Logout
    </button>
  </div>

</div>

login.component.ts (note that logout() works)

import { Component, OnInit, Inject } from '@angular/core';
import { Router } from '@angular/router';
import { AuthService, User } from '@auth0/auth0-angular';
import { OnlineStatusService, OnlineStatusType } from 'ngx-online-status';
import { DOCUMENT } from '@angular/common';


@Component({
  selector: 'app-login',
  templateUrl: './login.component.html',
  styleUrls: ['./login.component.css']
})
export class LoginComponent implements OnInit {

  constructor(
    public auth: AuthService,
    private router: Router,
    private onlineStatusService: OnlineStatusService,
    @Inject(DOCUMENT) public document: Document
  ) {

  }

  ngOnInit(): void {
    this.auth.user$.subscribe((value: User | null | undefined) => {
      console.log("User:", value);
    });

    this.auth.isAuthenticated$.subscribe((value: boolean) => {
      console.log("Authd:", value);
    });
  }

  // attempt to login with the entered credentials
  // solution from https://community.auth0.com/t/isauthenticated-is-always-false/84794/3
  attemptLogin(): void {
    this.auth.isAuthenticated$.subscribe((value: boolean) => {
      if (!value) {
        let query: string = window.location.search;
        let shouldParseResult: boolean = query.includes("code=") && query.includes("state=");
        if (shouldParseResult) {
          try {
            this.auth.handleRedirectCallback().subscribe((value) => {
              console.log("Logged in!", value);
            });
          } catch (err: unknown) {
            console.log("Error parsing redirect:", err);
          }
          window.history.replaceState({}, this.document.title, "/");
        }
        else {
          this.auth.loginWithRedirect().subscribe((value: void) => {
            console.log("Logging in...", value);
          });
        }
      }
      else {
        this.router.navigate(['home']);
      }
    });
  }

  // log out of account and go back to login screen
  logout(): void {
    if (this.onlineStatusService.getStatus() === OnlineStatusType.OFFLINE) {
      this.router.navigate(['login']);
      return;
    }
    this.auth.logout({
      logoutParams: {
        returnTo: this.document.location.origin
      }
    });
  }
}


01/24/2023 update: I think I know what is happening. When a user is unauthenticated in both my app and on Auth0, loginWithRedirect() works. After logging in, Auth0 says that I am authenticated, taking me back to my app. However, for some reason, in my app, it says that I am not authenticated. This then causes loginWithRedirect() to execute again. However, Auth0 says that I am already authenticated, taking me back to my app. This causes an infinite loop where my app says that I am unauthenticated, launching loginWithRedirect(), while Auth0 says that I am authenticated, taking me back to my app.

Essentially, for some reason, loginWithRedirect() causes my app to never recognize a user as authenticated, while the Auth0 API does when logging in. Note that this does not happen with AuthGuard. With AuthGuard, authentication recognition works perfectly in my app.


01/25/2023 update: Getting loginWithRedirect() to work may be necessary at this point for building my app. I need my app to detect if a user is online or not, which it currently can. If a user is online, they should authenticate regularly by connecting to Auth0. If a user is offline, they should authenticate through the last retrieved access token while they were online. I do not know if I can do that with canActivate: [AuthGuard] on each screen.


01/26/2023 update: loginWithPopup() now works with this solution. Abandoned the AuthGuard solution. Unfortunately, loginWithRedirect() still does not work with any of the solutions that I have found.

Trying to delete the “management-api” tag but it won’t let me. I realized this morning that that tag is not relevant to this post.

I found an alternative solution that bypasses using loginWithRedirect(). You can use AuthGuard for each screen instead:

app-routing.module.ts

import { AuthGuard } from '@auth0/auth0-angular';

const routes: Routes = [
  { path: '', redirectTo: '/home', pathMatch: 'full' },
  { path: 'sign-up', component: SignUpComponent, canActivate: [AuthGuard] },
  { path: 'home', component: HomeComponent, canActivate: [AuthGuard] },
  { path: 'profile', component: ProfileComponent, canActivate: [AuthGuard] },
  { path: 'settings', component: SettingsComponent, canActivate: [AuthGuard] }
];

I’d prefer a solution that uses loginWithRedirect(), but this works for now. Not marking this as the solution unless there is no solution involving loginWithRedirect().

This topic was automatically closed 14 days after the last reply. New replies are no longer allowed.