Mira la lección en vídeo
Accede al vídeo completo de esta lección y a más contenido exclusivo con el Plan Plus.
Desbloquear Plan PlusIntroducción a JWT
Los JSON Web Tokens (JWT) en Angular son cruciales para desarrolladores que buscan implementar autenticación y autorización seguras en sus aplicaciones web. JWT ofrece una manera compacta y autónoma de transmitir información segura entre partes como un objeto JSON. Esta información puede ser verificada y confiada porque está firmada digitalmente. Angular, siendo uno de los frameworks más populares para el desarrollo de aplicaciones web, proporciona un ecosistema adecuado para integrar JWT en la gestión de sesiones de usuario.
Historia y origen de JWT
JSON Web Tokens (JWT) surgieron como una solución a la necesidad de un estándar de tokens de acceso que permitiera la comunicación entre diferentes sistemas de manera segura. Su especificación, definida en el RFC 7519, establece cómo los tokens pueden ser usados para intercambiar información entre dos partes de manera segura. Esta característica los ha hecho sumamente populares en la implementación de autenticación y autorización en aplicaciones web modernas, incluyendo aquellas desarrolladas con Angular.
Los JWT son importantes porque proporcionan un método estandarizado y ligero para la autenticación de usuarios y la autorización de solicitudes, sin necesidad de mantener un estado de sesión en el servidor. Esto es especialmente útil en arquitecturas de aplicaciones distribuidas y microservicios. Además, su capacidad para ser firmados digitalmente asegura que la información que contienen puede ser verificada y confiada sin necesidad de una consulta adicional al servidor de autenticación.
Diferenciación de JWT de otros métodos de autenticación
Los JSON Web Tokens (JWT) representan un avance significativo en la autenticación y autorización de aplicaciones web comparados con métodos tradicionales, como las sesiones basadas en cookies.
A diferencia de las cookies, que requieren almacenamiento del estado de la sesión en el servidor, los JWT son autónomos y contienen toda la información necesaria para verificar la identidad del usuario. Esta característica los hace ideales para aplicaciones escalables y distribuidas, donde mantener el estado de la sesión entre múltiples servidores puede ser problemático.
Además, los JWT pueden ser fácilmente transmitidos entre diferentes dominios y servicios, facilitando patrones de diseño como Single Sign-On (SSO) y comunicaciones entre microservicios, lo que contribuye a su popularidad y adopción generalizada en la industria.
Aplicaciones prácticas
- Autenticación de usuario: En aplicaciones Angular, los JWT se usan comúnmente para autenticar usuarios. Después de que un usuario se autentica, el servidor genera un JWT que luego se devuelve al cliente y se almacena, típicamente en el almacenamiento local del navegador.
- Autorización de solicitudes: Los JWT son enviados en los encabezados de las solicitudes HTTP para acceder a recursos protegidos en el servidor, permitiendo una fácil autorización de solicitudes basada en tokens.
- Single Sign-On (SSO): Los JWT son una base para implementar SSO, permitiendo que los usuarios se autentiquen una vez y accedan a varios servicios sin necesidad de volver a autenticarse.
Implementación JWT en Angular
La autenticación con JWT implica dos partes principales: el proceso de inicio de sesión, donde el servidor valida las credenciales del usuario y genera un token; y el uso del token para futuras solicitudes que requieran autenticación. En Angular, este proceso se maneja a través de servicios y componentes que interactúan con el backend y almacenan el token en el cliente.
Paso 1: Crear el servicio de autenticación auth.service.ts
El AuthService
es el corazón de nuestro sistema de autenticación. Este servicio se encarga de:
- Enviar las credenciales del usuario al servidor y recibir el JWT.
- Almacenar el JWT de manera segura en el almacenamiento local del navegador.
- Proveer un mecanismo para verificar si el usuario está autenticado.
Implementación:
import { Injectable } from '@angular/core';
import { HttpClient } from '@angular/common/http';
import { BehaviorSubject } from 'rxjs';
import { tap } from 'rxjs/operators';
@Injectable({
providedIn: 'root'
})
export class AuthService {
private isLoggedIn = new BehaviorSubject<boolean>(false);
constructor(private http: HttpClient) {}
// Inicia sesión y almacena el JWT
login(username: string, password: string) {
return this.http.post<{token: string}>('https://yourapi.com/login', { username, password })
.pipe(
tap(response => {
localStorage.setItem('access_token', response.token); // Almacena el token
this.isLoggedIn.next(true); // Actualiza el estado de autenticación
})
);
}
// Verifica si el usuario está autenticado
isAuthenticated() {
return this.isLoggedIn.asObservable();
}
}
Puntos clave:
BehaviorSubject<boolean>
: Mantiene el estado de autenticación que puede ser consumido por otros componentes o servicios.localStorage.setItem('access_token', response.token)
: Almacena el token en el almacenamiento local, asegurando que permanezca disponible durante las sesiones del navegador.
Paso 2: Crear componente de inicio de sesión
El componente de inicio de sesión proporciona una interfaz de usuario para que los usuarios ingresen sus credenciales. Interactúa con el AuthService
para iniciar la sesión.
Guarda tu progreso
Inicia sesión para no perder tu progreso y accede a miles de tutoriales, ejercicios prácticos y nuestro asistente de IA.
Más de 25.000 desarrolladores ya confían en CertiDevs
Implementación:
import { Component } from '@angular/core';
import { AuthService } from '../auth.service';
@Component({
selector: 'app-login',
template: `
<form (submit)="login()">
<input type="text" [(ngModel)]="username" name="username" placeholder="Username">
<input type="password" [(ngModel)]="password" name="password" placeholder="Password">
<button type="submit">Login</button>
</form>
`
})
export class LoginComponent {
username: string = '';
password: string = '';
constructor(private authService: AuthService) {}
// Función de inicio de sesión que utiliza AuthService
login() {
this.authService.login(this.username, this.password).subscribe();
}
}
Puntos clave:
- Formulario de inicio de sesión: Recoge las credenciales del usuario y las envía al
AuthService
. - Modelo de Two-Way Binding con [(ngModel)]: Permite una interacción fluida entre la vista (formulario) y el componente.
Otra opción es crear un formulario reactivo:
<form [formGroup]="loginForm" (ngSubmit)="save()">
<h1 class="h3 mb-3 fw-normal">Iniciar sesión</h1>
<div class="form-floating">
<input type="email" class="form-control" id="email" placeholder="name@example.com" formControlName="email">
<label for="email">Email address</label>
</div>
<div class="form-floating">
<input type="password" class="form-control" id="password" placeholder="Password" formControlName="password">
<label for="password">Password</label>
</div>
<button class="btn btn-primary w-100 py-2" type="submit">Iniciar sesión</button>
@if(errorMessage && errorMessage.length > 0) {
<small class="text-danger">{{errorMessage}}</small>
}
</form>
Paso 3: Crear el Interceptor auth.interceptor.ts
Este interceptor interceptará todas las solicitudes HTTP salientes. Si existe un JWT almacenado (por ejemplo, en el almacenamiento local del navegador), el interceptor añadirá este token al encabezado de autorización de cada solicitud.
Implementación:
import { Injectable } from '@angular/core';
import { HttpInterceptor, HttpRequest, HttpHandler } from '@angular/common/http';
@Injectable()
export class AuthInterceptor implements HttpInterceptor {
intercept(req: HttpRequest<any>, next: HttpHandler) {
const token = localStorage.getItem('access_token'); // Obtiene el JWT del almacenamiento local
if (token) {
// Si existe un token, clona la solicitud y añade el encabezado de autorización
const cloned = req.clone({
headers: req.headers.set("Authorization", "Bearer " + token)
});
return next.handle(cloned); // Pasa la solicitud modificada al siguiente manejador
} else {
return next.handle(req); // Pasa la solicitud original al siguiente manejador si no hay token
}
}
}
Puntos clave:
localStorage.getItem('access_token')
: Recupera el token de autenticación del almacenamiento local.req.clone({...})
: Crea una copia de la solicitud original y modifica los encabezados para incluir el token de autenticación.
Paso 4: Registrar el interceptor en el módulo principal app.module.ts
Para que el interceptor sea efectivo, debe ser registrado en el módulo principal de la aplicación Angular (AppModule
). Esto se hace proporcionando el interceptor como un proveedor en el nivel de módulo.
Implementación:
import { HTTP_INTERCEPTORS } from '@angular/common/http';
import { AuthInterceptor } from './auth.interceptor';
@NgModule({
declarations: [
// Otros componentes
],
imports: [
// Otros módulos
],
providers: [
{ provide: HTTP_INTERCEPTORS, useClass: AuthInterceptor, multi: true },
// Añade aquí otros servicios si es necesario
],
bootstrap: [AppComponent]
})
export class AppModule { }
Puntos clave:
HTTP_INTERCEPTORS
: Un token de inyección especial de Angular que permite a los interceptores ser agregados a la cadena de manejo de solicitudes.multi: true
: Indica queHTTP_INTERCEPTORS
es un token multi-proveedor, permitiendo múltiples interceptores que se ejecutan en el orden en que fueron proporcionados.
Aprendizajes de esta lección de Angular
- Comprender el concepto y la estructura de JWT.
- Integrar JWT en aplicaciones Angular.
- Autorización y protección de rutas con JWT.
- Uso de interceptores HTTP para añadir JWT a solicitudes.
- Creación y validación de JWT en el servidor.
Completa este curso de Angular y certifícate
Únete a nuestra plataforma de cursos de programación y accede a miles de tutoriales, ejercicios prácticos, proyectos reales y nuestro asistente de IA personalizado para acelerar tu aprendizaje.
Asistente IA
Resuelve dudas al instante
Ejercicios
Practica con proyectos reales
Certificados
Valida tus conocimientos
Más de 25.000 desarrolladores ya se han certificado con CertiDevs