Hakim
Hakim

Reputation: 3437

Unable to refresh the router menu in Angular 4

I'm unable to have the router menu update itself when doing a router.navigateByUrl in Angular 4.

What I'm doing is really basic, I'm just trying to hide the login/logout menu when the user isn't/is authenticated. Below is my app.component.html:

<h1>
  {{ appName }}
</h1>

<nav>
    <a *ngIf="!isLogged" routerLink="/login">Login</a>
    <a *ngIf="isLogged" routerLink="/logout">Logout</a>
</nav>

<router-outlet></router-outlet>

And here is my app.component.ts:

import { Component } from '@angular/core';
import { AuthService } from './services/auth.service';
import { Router } from '@angular/router';

@Component({
    selector: 'app-root',
    templateUrl: './app.component.html',
    styleUrls: ['./app.component.css']
})
export class AppComponent {
    isLogged: boolean;

    // inject auth
    constructor(private auth: AuthService, private router: Router) { }

    ngOnInit() {
        this.isLogged = this.auth.isLogged;
        console.log('[app] islogged:' + this.auth.isLogged);

        // redirect according to whether user logged in
        if (this.isLogged)
            this.router.navigateByUrl('/total');
        else
            this.router.navigateByUrl('/login');
    }
}

As you can tell, Login and Logout are two separate components. To show which part of the code is responsible for this issue, below is the LogoutComponent::ngOnInit():

ngOnInit() {
    // logout
    this.auth.logout();

    // redirect to /login
    this.router.navigateByUrl('');
}

The last command is able to redirect to the / but the menu isn't updated according to the template posted in the first code.

Edit: This is the service used to login/logout users:

import { Injectable } from '@angular/core';

@Injectable()
export class AuthService {
    isLogged: boolean = false;
    token: string;

    constructor() { }

    login(token: string) {
        // save token on login
        this.isLogged = true;
        this.token = token;
    }

    logout() {
        // delete token on logout
        this.isLogged = false;
        this.token = '';
    }
}

Upvotes: 0

Views: 617

Answers (1)

Sajeetharan
Sajeetharan

Reputation: 222582

change it based on the route as,

this.router.navigate(['/login']);

While the above will solve your navigation issue.In addition to that, the actual problem lies with the way you update isLogged variable in your app.component.html

According to the way you have right now, it wont get updated whenever it is updated in other components. So you should have the shared service with a variable subject, which would watch for changes.

Something like this,

export class AppMessageQueuService {
    authenticatedUserData: Subject<LoginInfo>;
    constructor() {
        this.authenticatedUserData = new Subject<LoginInfo>();
    }
}

Upvotes: 1

Related Questions