¿Qué es la actualización sin interrupciones y cómo implementarla?
- 910Palabras
- 5Minutos
- 09 Aug, 2024
La actualización sin interrupciones es un mecanismo que permite a las aplicaciones frontend solicitar automáticamente nuevos tokens cuando el token actual está a punto de expirar, sin requerir intervención del usuario. Este enfoque mejora la experiencia del usuario y evita interrupciones en la sesión debido a la expiración del token.
Métodos Comunes para Implementar Actualización Sin Interrupciones
Gestión del Tiempo de Expiración del Token
- Después de que el usuario inicia sesión, la aplicación frontend generalmente almacena el token de acceso (como JWT) y el token de actualización.
- El token de acceso suele tener un período de validez corto (por ejemplo, 15 minutos), mientras que el token de actualización tiene una validez más prolongada (por ejemplo, 7 días).
- La aplicación frontend solicita activamente un nuevo token de acceso usando el token de actualización cuando el token de acceso está a punto de expirar (por ejemplo, cuando quedan 2 minutos).
Interceptor
- La aplicación frontend puede usar interceptores (como en Axios o Fetch) para interceptar todas las solicitudes.
- Si se detecta que el token de acceso actual ha expirado, el interceptor primero usa el token de actualización para obtener un nuevo token de acceso y luego reenvía la solicitud original.
- De esta manera, el usuario no percibe ninguna interrupción y la aplicación mantiene la operación continua.
Lógica de Actualización Sin Interrupciones
- Configurar un temporizador para activar automáticamente la operación de actualización antes de que el token esté a punto de expirar.
- Verificar periódicamente el período de validez del token y actualizarlo automáticamente si está a punto de expirar, para evitar interrupciones en la operación del usuario.
- Si el token de actualización también ha expirado, redirigir al usuario a la página de inicio de sesión.
Autenticación Silenciosa
- Para algunas aplicaciones frontend, se puede usar un iFrame oculto para realizar la autenticación silenciosa, utilizando el mecanismo de SSO para completar la actualización del token en segundo plano sin afectar la operación del usuario en la interfaz principal.
Ejemplo de Implementación de Interceptor en Axios
A continuación se muestra un ejemplo completo de implementación de un interceptor de Axios para manejar la actualización automática de tokens JWT y reintentos de solicitudes. En este ejemplo, se supone que ya tienes una API backend que proporciona la funcionalidad de actualización de tokens.
1. Crear una Instancia de Axios
Primero, necesitamos crear una instancia de Axios y configurar los interceptores de solicitudes y respuestas.
1import axios from "axios";2
3// Crear instancia de Axios4const apiClient = axios.create({5 baseURL: "https://api.example.com", // Reemplaza con tu URL base de API6 timeout: 10000,7});
2. Añadir Interceptor de Solicitudes
Añadir el encabezado de Authorization en cada solicitud para incluir el token de acceso JWT.
1// Añadir interceptor de solicitudes2apiClient.interceptors.request.use(3 (config) => {4 // Incluir el encabezado Authorization en cada solicitud5 const token = localStorage.getItem("token");6 if (token) {7 config.headers["Authorization"] = `Bearer ${token}`;8 }9 return config;10 },11 (error) => {12 // Manejar errores de solicitud13 return Promise.reject(error);14 },15);
3. Añadir Interceptor de Respuestas
Manejar los errores 401 y usar el token de actualización para obtener un nuevo token de acceso cuando el token expira.
1// Añadir interceptor de respuestas2apiClient.interceptors.response.use(3 (response) => {4 // Retornar directamente los datos de la respuesta5 return response;6 },7 async (error) => {8 const originalRequest = error.config;9
10 // Si el código de estado de la respuesta es 401 y la solicitud original no se ha reintentado11 if (12 error.response &&13 error.response.status === 401 &&14 !originalRequest._retry15 ) {16 originalRequest._retry = true;17 try {18 const refreshToken = localStorage.getItem("refreshToken");19 if (refreshToken) {20 // Enviar solicitud de token de actualización21 const { data } = await axios.post(22 "https://api.example.com/auth/refresh",23 { token: refreshToken },24 );25
26 // Actualizar el token almacenado localmente27 localStorage.setItem("token", data.token);28
29 // Actualizar el encabezado Authorization30 axios.defaults.headers.common["Authorization"] =31 `Bearer ${data.token}`;32
33 // Reenviar la solicitud original34 originalRequest.headers["Authorization"] = `Bearer ${data.token}`;35 return apiClient(originalRequest);36 }37 } catch (refreshError) {38 // Si el token de actualización también ha expirado, redirigir a la página de inicio de sesión39 localStorage.removeItem("token");40 localStorage.removeItem("refreshToken");41 window.location.href = "/login";42 }43 }44
45 // Manejar otros errores46 return Promise.reject(error);47 },48);49
50export default apiClient;
Explicación del Código
-
Instanciación de Axios:
Se utiliza
axios.create()
para crear una instancia personalizada de AxiosapiClient
, que puede tener una URL base y otras configuraciones. -
Interceptor de Solicitudes:
Antes de que se envíe cada solicitud, se verifica si existe un token de acceso JWT. Si existe, se agrega al encabezado
Authorization
de la solicitud. -
Interceptor de Respuestas:
- Manejo de Errores 401: Cuando el servidor devuelve un error 401, esto indica que el token podría haber expirado.
- Actualización del Token: Si existe un token de actualización, se envía una solicitud al endpoint de la API para obtener un nuevo token de acceso.
- Actualización del Token: El nuevo token se almacena localmente y se actualizan los encabezados de solicitudes de Axios para usar el nuevo token en solicitudes futuras.
- Reintento de Solicitud: La solicitud original se reenvía utilizando el nuevo token.
-
Fallo en la Actualización del Token:
Si el token de actualización también es inválido o ha expirado, se eliminan los tokens almacenados localmente y se redirige al usuario a la página de inicio de sesión.
Cómo Usar
En la aplicación, puedes usar apiClient
en lugar del Axios original para enviar solicitudes HTTP:
1import apiClient from "./apiClient";2
3async function getUserData() {4 try {5 const response = await apiClient.get("/user/profile");6 console.log(response.data);7 } catch (error) {8 console.error("Error al obtener los datos del usuario:", error);9 }10}
Este código utiliza el apiClient
encapsulado para enviar solicitudes, manejando automáticamente la actualización y reintento del token.
Conclusión
Con los métodos descritos, puedes implementar la actualización sin interrupciones en aplicaciones frontend, asegurando que los usuarios no sean interrumpidos debido a la expiración del token. Este mecanismo mejora la experiencia del usuario y hace que la aplicación sea más fluida.