En esta lección vamos a:
- Configurar Spring Security para proteger tu aplicación.
- Conectar y configurar JWT para la autenticación.
- Implementar la verificación de tokens y las reglas de acceso para la API.
- Aprender cómo generar y validar tokens JWT.
Configuración de Spring Security
Spring Security — es como una navaja suiza, pero para la seguridad de aplicaciones. Soporta de todo: desde autenticación y autorización hasta mecanismos de cifrado complejos. Empecemos con una configuración básica y luego añadimos JWT.
Añadir la dependencia
Si usas Maven, añade en pom.xml esta dependencia:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-security</artifactId>
</dependency>
Si usas Gradle:
implementation 'org.springframework.boot:spring-boot-starter-security'
Crear la clase de configuración básica
Crearemos una clase de configuración para Spring Security:
@Configuration
@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter {
@Override
protected void configure(HttpSecurity http) throws Exception {
http.csrf().disable() // Desactivamos CSRF para APIs REST
.authorizeRequests()
.antMatchers("/api/auth/**").permitAll() // Permitimos el acceso al API de autenticación
.anyRequest().authenticated() // Todas las demás peticiones requieren autenticación
.and()
.sessionManagement().sessionCreationPolicy(SessionCreationPolicy.STATELESS); // JWT = Stateless
}
}
JSON Web Token (JWT): ¿qué es y para qué sirve?
JWT — es un estándar que se usa para transmitir datos entre cliente y servidor en un formato firmado. Es como una caja fuerte con contraseña: quien tiene la llave (la clave secreta), puede "abrirla" y leer su contenido.
Cada JWT consta de tres partes:
- Header (encabezado) — información sobre el tipo de token y el algoritmo de cifrado.
- Payload (carga útil) — aquí se almacenan los datos del usuario (ID, roles).
- Signature (firma) — se usa para verificar la autenticidad del token.
Generación de tokens JWT
Para trabajar con JWT usaremos la librería jjwt. Conéctala en tu pom.xml:
<dependency>
<groupId>io.jsonwebtoken</groupId>
<artifactId>jjwt-api</artifactId>
<version>0.11.5</version>
</dependency>
Ahora vamos a crear una clase utilitaria para trabajar con tokens.
import io.jsonwebtoken.*;
import org.springframework.stereotype.Component;
import java.util.Date;
@Component
public class JwtTokenUtil {
private final String SECRET_KEY = "secret"; // ¡Usa una clave más compleja!
public String generateToken(String username) {
return Jwts.builder()
.setSubject(username) // Establecemos el usuario
.setIssuedAt(new Date()) // Fecha de emisión del token
.setExpiration(new Date(System.currentTimeMillis() + 1000 * 60 * 60 * 10)) // El token expira en 10 horas
.signWith(SignatureAlgorithm.HS256, SECRET_KEY) // Algoritmo de firma
.compact();
}
public String extractUsername(String token) {
return Jwts.parser()
.setSigningKey(SECRET_KEY)
.parseClaimsJws(token)
.getBody()
.getSubject();
}
public boolean validateToken(String token) {
try {
Jwts.parser().setSigningKey(SECRET_KEY).parseClaimsJws(token);
return true;
} catch (JwtException | IllegalArgumentException e) {
return false; // Token inválido
}
}
}
Añadir un filtro para validar tokens
Ahora escribiremos un filtro que procese cada petición y valide el JWT.
Implementación de endpoints para autenticación
Ahora crearemos un controlador que genere tokens JWT:
@RestController
@RequestMapping("/api/auth")
public class AuthController {
private final JwtTokenUtil jwtTokenUtil;
public AuthController(JwtTokenUtil jwtTokenUtil) {
this.jwtTokenUtil = jwtTokenUtil;
}
@PostMapping("/login")
public ResponseEntity
createAuthenticationToken(@RequestBody AuthRequest authRequest) {
// Aquí puedes añadir la lógica para verificar usuarios (por ejemplo, contra una base de datos)
String token = jwtTokenUtil.generateToken(authRequest.getUsername());
return ResponseEntity.ok(new AuthResponse(token));
}
}
class AuthRequest {
private String username;
private String password;
// getters/setters
}
class AuthResponse {
private final String token;
public AuthResponse(String token) {
this.token = token;
}
public String getToken() {
return token;
}
}
Resumen: ¿qué hicimos?
Configuramos Spring Security, implementamos tokens JWT y añadimos una protección básica a tu REST API. Ahora tu aplicación es mucho más segura.
GO TO FULL VERSION