I have a Customer component and a Dashboard component and then the login component, but I can't redirect to the login if it hasn't entered:
I have a security folder with an auth.guard.ts file:
import { Injectable } from "@angular/core";
import { Router,CanActivate,ActivatedRouteSnapshot } from "@angular/router";
@Injectable ({providedIn:'root'})
export class AuthGuard implements CanActivate{
constructor(private route : Router){
}
canActivate(route: ActivatedRouteSnapshot){
this.route.navigate(['login']);
return false;
}
}
And this is my app.module.ts:
import { BrowserModule } from "@angular/platform-browser";
import { NgModule,Input } from "@angular/core";
import { BrowserAnimationsModule } from "@angular/platform-browser/animations";
import { Routes, RouterModule } from "@angular/router";
import { platformBrowserDynamic } from '@angular/platform-browser-dynamic';
// material
import { MatSidenavModule } from "@angular/material/sidenav";
import { MatIconModule } from "@angular/material/icon";
import { MatListModule } from "@angular/material/list";
import { MatTooltipModule } from "@angular/material/tooltip";
import { MatButtonModule } from "@angular/material/button";
import { MatTableModule } from '@angular/material/table' ;
import { MatCardModule } from '@angular/material/card' ;
import { MatDialogModule} from '@angular/material/dialog' ;
import {MatInputModule} from '@angular/material/input';
import {MatSnackBarModule} from '@angular/material/snack-bar';
// components
import { AppComponent } from "./app.component";
import { SidenavComponent } from "./sidenav/sidenav.component";
import { HomeComponent } from "./home/home.component";
import { ClienteComponent } from './cliente/cliente.component';
import { HttpClientModule } from "@angular/common/http";
import { DialogClienteComponent } from "./cliente/dialog/dialogcliente.component";
import { FormsModule,ReactiveFormsModule } from "@angular/forms";
import { DialogDeleteComponent } from "./cliente/common/dialogdelete.component";
import { LoginComponent } from "./login/login.component";
export const ROUTES: Routes = [
{
path: "Home",
component: HomeComponent,
},
{
path: "login",
component: LoginComponent,
},
{
path: "Clientes",
component: ClienteComponent,
},
];
@NgModule({
declarations: [
AppComponent,
DialogClienteComponent,
DialogDeleteComponent,
SidenavComponent,
LoginComponent,
ClienteComponent
],
imports: [
RouterModule.forRoot(ROUTES, { relativeLinkResolution: 'legacy' }),
BrowserModule,
BrowserAnimationsModule,
MatSidenavModule,
MatListModule,
MatIconModule,
MatTooltipModule,
MatButtonModule,
MatTableModule,
MatDialogModule,
MatInputModule,
MatSnackBarModule,
MatCardModule,
HttpClientModule,
FormsModule,
ReactiveFormsModule,
],
bootstrap: [AppComponent],
})
export class AppModule {}
I don't know if someone can help me, if you need another code I'll edit the question.
My app.routing has the following:
import { NgModule } from '@angular/core';
import { RouterModule, Routes } from '@angular/router';
import { ClienteComponent } from './cliente/cliente.component';
import { HomeComponent } from './home/home.component';
import { LoginComponent } from './login/login.component';
import { AuthGuard } from './security/auth.guard';
const routes: Routes = [
{ path: '', redirectTo: 'login', pathMatch: 'full' },
{ path: '**', redirectTo: 'login' },
{path: 'home',component:HomeComponent,canActivate:[AuthGuard]},
{path: 'Clientes',component:ClienteComponent,canActivate:[AuthGuard]},
{path: 'login',component:LoginComponent}
];
@NgModule({
imports: [RouterModule.forRoot(routes)],
exports: [RouterModule]
})
export class AppRoutingModule { }
There I show my login component:
import {Component, OnInit } from "@angular/core";
import { Router } from "@angular/router";
import { ApiAuthService } from "../services/apiauth.service";
@Component({templateUrl:'login.component.html'})
export class LoginComponent implements OnInit{
public user!: string;
public password!: string;
constructor(public apiauth:ApiAuthService,
private router:Router){
if (this.apiauth.usuarioData){
this.router.navigate(['/']);
}
}
ngOnInit(){
}
login(){
this.apiauth.login(this.user,this.password).subscribe(response =>{
if (response.exito===1) {
this.router.navigate(['/']);
}
});
}
}
And my apiauthservice.ts:
import { HttpClient, HttpHeaders } from "@angular/common/http";
import { Injectable } from "@angular/core";
import { BehaviorSubject, map, Observable } from "rxjs";
import { Usuario } from "../models/usuario";
import { Response } from "../models/response";
const httpOption = {
headers :new HttpHeaders({
'Content-Type' : 'application/json'
})
}
@Injectable({
providedIn:'root'
})
export class ApiAuthService{
url: string = 'https://localhost:44355/Login' ;
private usuarioSubject!: BehaviorSubject<Usuario>;
public get usuarioData():Usuario{
return this.usuarioSubject.value;
}
constructor(private http : HttpClient){
this.usuarioSubject = new BehaviorSubject<Usuario>(JSON.parse(localStorage.getItem('usuario')!));
}
login(user: string, password:string):Observable<Response>{
return this.http.post<Response>(this.url, {user,password},httpOption).pipe(map(res=>{
if(res.exito === 1){
const usuario:Usuario = res.data;
localStorage.setItem('usuario',JSON.stringify(usuario));
this.usuarioSubject.next(usuario);
}
return res;
}));
}
logout(){
localStorage.removeItem('usuario');
this.usuarioSubject.next(null!);
}
}
The canActivate stayed like this but it still doesn't work:
canActivate(route: ActivatedRouteSnapshot){
const usuario = this.apiauthservice.usuarioData;
if (usuario){
return true;
}else{
this.route.navigate(['login']);
return false;
}
Add the
/
to complete the path.I think that the route variable that your canActivate receives is the one with the problem, since you would be using the one from the method and not the one from the constructor, your router variable would be converted to a scoop variable. I hope it works for you.
It was solved by modifying app.module.ts, adding the
AuthGuard
in the routes, although the tutorial I saw had it in app.routing.ts as published in the question: