Security — Auth, JWT & Method Security
Spring Security
Spring Security schützt Endpoints, Methoden und Daten. Default: alle Routen sind authentifiziert.
Lektion 36: SecurityFilterChain
@Configuration
@EnableWebSecurity
public class SecurityConfig {
@Bean
SecurityFilterChain filterChain(HttpSecurity http) throws Exception {
return http
.csrf(csrf -> csrf.disable())
.authorizeHttpRequests(auth -> auth
.requestMatchers("/api/public/**").permitAll()
.requestMatchers("/api/admin/**").hasRole("ADMIN")
.anyRequest().authenticated()
)
.sessionManagement(s -> s.sessionCreationPolicy(SessionCreationPolicy.STATELESS))
.oauth2ResourceServer(o -> o.jwt(Customizer.withDefaults()))
.build();
}
}
Lektion 37: Authentifizierung mit JWT
@Bean
JwtDecoder jwtDecoder() {
return NimbusJwtDecoder.withSecretKey(
Keys.hmacShaKeyFor(System.getenv("JWT_SECRET").getBytes())
).build();
}
JWT = Header.Payload.Signature. Stateless: kein Server-Session nötig.
Stateless vs. Stateful Auth
Stateless (JWT): Server speichert keine Session. Skaliert horizontal. Token enthält Claims (sub, roles, exp). Stateful (Session): Server speichert Session-ID. Einfacher zu invalidieren, aber schwerer zu skalieren.
Lektion 38: Passwort-Hashing
@Bean
PasswordEncoder passwordEncoder() {
return new BCryptPasswordEncoder(12); // cost factor
}
Nie Klartext-Passwörter. BCrypt mit cost factor 12 ist Standard.
Lektion 39: Method-Level Security
@Service
public class AdminService {
@PreAuthorize("hasRole('ADMIN')")
public void deleteUser(Long id) { /* ... */ }
@PostAuthorize("returnObject.owner == authentication.name")
public Document getDocument(Long id) { /* ... */ }
}
@PreAuthorize prüft vor der Ausführung, @PostAuthorize nach der Ausführung.
Lektion 40: Security-Kontext & Testing
@Test
@WithMockUser(roles = "ADMIN")
void adminCanDelete() throws Exception {
mockMvc.perform(delete("/api/admin/users/1"))
.andExpect(status().isNoContent());
}
JWT-Trade-offs: Stateless heisst auch schwer widerrufbar
JWTs sind bis zum Ablauf gültig — ein geleakter Token lässt sich nicht einfach invalidieren. Gegenmassnahmen: kurze Laufzeiten (z. B. 1 h), Refresh-Tokens serverseitig, oder eine Blacklist. Faustregel: so kurz wie möglich, so lang wie nötig.
Praxis-Szenario: CropGuard: Rollen im JWT
JwtService schreibt beim Login die Rolle (FARMER/ASSESSOR) in einen Claim. Der JwtAuthFilter liest den Bearer-Token, validiert die Signatur und setzt den SecurityContext.
✅ Wichtige Erkenntnisse
Haken setzen, um deinen Lernfortschritt zu markieren: