• v1.2.0 96e5b62aef

    github-actions[bot] released this 2026-05-08 22:15:20 +02:00 | 276 commits to main since this release

    v1.2.0 - Auth and Users

    Release Date: 2026-05-08

    Milestone: v1.2.0 (Auth and Users)

    This milestone delivers a complete authentication and user management system with modern password hashing and JWT-based stateless authentication. All API endpoints now require authentication, providing a secure foundation for multi-user platform access.

    Added

    User Management with Argon2id Password Hashing

    • PasswordHashingService using Argon2id algorithm for secure password storage
      • 64MB memory requirement (m=65536)
      • 3 iterations (t=3)
      • Parallelism factor of 1 (p=1)
      • Argon2id variant for resistance to both GPU cracking attacks and side-channel attacks
      • Bouncy Castle provider (bcprov-jdk18on 1.78.1) for Argon2 implementation
      • Constant-time hash comparison to prevent timing attacks
      • PHC string format: $argon2id$v=19$m=65536,t=3,p=1$[salt]$[hash]

    User CRUD APIs

    • UserController REST endpoints:

      • GET /api/users - List all users
      • GET /api/users/{id} - Get user by ID
      • POST /api/users - Create new user with password hashing
      • PATCH /api/users/{id} - Update user (username, email, role)
      • PATCH /api/users/{id}/password - Change user password
      • DELETE /api/users/{id} - Delete user
    • UserService enhancements:

      • create(user, plainPassword) - Hash password and create user
      • update(id, updates) - Update user with change tracking
      • updatePassword(id, newPlainPassword) - Securely change password
      • Username and email uniqueness validation
      • Structured logging for all user operations (create, update, password change, delete)
      • Change tracking for user updates (before/after values logged)
    • DTOs:

      • UpdatePasswordRequest - Password change request validation
      • UpdateUserRequest - User update with email and role validation

    JWT Infrastructure

    • JJWT library version 0.12.6 for JWT token management

      • jjwt-api - JWT API
      • jjwt-impl - JWT implementation
      • jjwt-jackson - Jackson integration for JSON serialization
    • JwtService for token generation and validation:

      • generateAccessToken(userId, username, role) - Create short-lived access token
      • generateRefreshToken(userId) - Create long-lived refresh token
      • parseToken(token) - Parse and validate JWT claims
      • isTokenValid(token) - Check token validity and expiration
      • Extract userId, username, role, and token type from tokens
      • Access tokens valid for 15 minutes (configurable via jwt.access-token-validity-ms)
      • Refresh tokens valid for 7 days (configurable via jwt.refresh-token-validity-ms)
      • Tokens signed with HS256 (HMAC-SHA256) algorithm
      • JWT secret configurable via jwt.secret property (MUST change in production)
    • Token Claims:

      • sub (subject) - User ID
      • username - Username
      • role - User role (OWNER, ADMIN, USER, VIEWER)
      • type - Token type (access or refresh)
      • iat - Issued at timestamp
      • exp - Expiration timestamp

    Authentication Endpoints

    • AuthenticationService:

      • login(username, password) - Authenticate user and generate tokens
      • refreshToken(refreshToken) - Generate new access token from refresh token
      • Password verification using PasswordHashingService
      • Structured logging for login attempts (success and failure)
      • Structured logging for token refresh operations
      • BadCredentialsException for invalid credentials or tokens
    • AuthenticationController REST endpoints:

      • POST /api/auth/login - User login with username and password
      • POST /api/auth/refresh - Refresh access token using refresh token
    • DTOs:

      • LoginRequest - Login credentials validation
      • RefreshTokenRequest - Refresh token validation
      • AuthenticationResponse - Login/refresh response with tokens and user info

    JWT Authentication and Authorization

    • JwtAuthenticationFilter:

      • Extracts JWT from Authorization: Bearer <token> header
      • Validates token signature and expiration
      • Only accepts access tokens (rejects refresh tokens)
      • Populates Spring Security context with user information
      • Creates UsernamePasswordAuthenticationToken with user ID as principal
      • Attaches JwtAuthenticationDetails with userId, username, and role
      • Grants ROLE_<role> authority for role-based authorization
      • Silently skips authentication for invalid/expired tokens (401 returned by framework)
    • SecurityContextHelper utility:

      • getCurrentUserId() - Get current authenticated user ID
      • getCurrentUsername() - Get current authenticated username
      • getCurrentUserRole() - Get current authenticated user role
      • isAuthenticated() - Check if user is authenticated
      • hasRole(role) - Check if user has specific role
    • SecurityConfig enhancements:

      • CSRF protection disabled (stateless JWT authentication)
      • Stateless session management
      • Method-level security enabled with @EnableMethodSecurity
      • Public endpoints: /api/auth/**, /api/health, /actuator/**
      • All other /api/** endpoints require authentication
      • JWT filter registered before UsernamePasswordAuthenticationFilter

    Security Features

    • Role-Based Access Control:

      • User roles: OWNER, ADMIN, USER, VIEWER
      • Spring Security authorities with ROLE_ prefix
      • Method security annotations supported: @PreAuthorize, @Secured, @RolesAllowed
    • Security Logging:

      • Login success and failure events
      • Token refresh events
      • User creation, updates, password changes, deletion
      • Failed login attempts logged with reason for security monitoring

    Changed

    • BREAKING CHANGE: All API endpoints now require authentication except:

      • /api/auth/** - Authentication endpoints
      • /api/health - Health check endpoint
      • /actuator/** - Spring Boot Actuator endpoints
    • User Management: All user operations now use Argon2id instead of BCrypt

      • Existing BCrypt hashes incompatible (users must reset passwords)

    Security Notes

    • Production Deployment:

      • MUST change jwt.secret property in production (default is for development only)
      • Recommended JWT secret length: at least 256 bits (32 characters) for HS256
      • Consider using environment variables for secret management
    • Token Security:

      • Access tokens are short-lived (15 minutes) to limit exposure window
      • Refresh tokens are long-lived (7 days) but minimal (only userId and type)
      • Only access tokens contain sensitive claims (username, role)
      • Tokens are stateless - no server-side session storage required
    • Password Security:

      • Argon2id with 64MB memory makes brute-force attacks computationally expensive
      • Constant-time comparison prevents timing attack exploitation
      • Salt is randomly generated per password (16 bytes)
      • Hash output is 32 bytes

    Configuration

    New configuration properties:

    jwt:
      secret: "CHANGE_ME_IN_PRODUCTION_THIS_MUST_BE_AT_LEAST_256_BITS_LONG_FOR_HS256"
      access-token-validity-ms: 900000  # 15 minutes
      refresh-token-validity-ms: 604800000  # 7 days
    

    Migration Guide

    For API Clients

    All API requests (except auth endpoints) now require authentication:

    # 1. Login to get tokens
    curl -X POST http://localhost:8080/api/auth/login \
      -H "Content-Type: application/json" \
      -d '{"username": "admin", "password": "password"}'
    
    # Response: {"accessToken": "...", "refreshToken": "...", "userId": "...", "username": "admin", "role": "ADMIN"}
    
    # 2. Use access token for authenticated requests
    curl http://localhost:8080/api/users \
      -H "Authorization: Bearer <accessToken>"
    
    # 3. Refresh access token when expired
    curl -X POST http://localhost:8080/api/auth/refresh \
      -H "Content-Type: application/json" \
      -d '{"refreshToken": "<refreshToken>"}'
    

    For Developers

    Access current user in Spring components:

    @Service
    public class MyService {
        private final SecurityContextHelper securityHelper;
        
        public void myMethod() {
            UUID userId = securityHelper.getCurrentUserId();
            String username = securityHelper.getCurrentUsername();
            String role = securityHelper.getCurrentUserRole();
            
            if (securityHelper.hasRole("ADMIN")) {
                // Admin-only logic
            }
        }
    }
    

    Use method security annotations:

    @PreAuthorize("hasRole('ADMIN')")
    public void adminOnlyMethod() {
        // Only ADMIN role can call this
    }
    
    @PreAuthorize("hasAnyRole('ADMIN', 'OWNER')")
    public void privilegedMethod() {
        // ADMIN or OWNER can call this
    }
    

    Technical Details

    • Dependencies:

      • Spring Boot Starter Security 4.0.0
      • JJWT 0.12.6 (jjwt-api, jjwt-impl, jjwt-jackson)
      • Bouncy Castle bcprov-jdk18on 1.78.1
    • Database Schema: Uses existing users table from v1.0.0

      • password_hash column stores Argon2id hashes in PHC format
    • Logging: All authentication and user management operations logged to system_logs table

      • Categories: AUTH, API
      • Events: USER_CREATED, USER_UPDATED, PASSWORD_UPDATED, USER_DELETED, LOGIN_SUCCESS, LOGIN_FAILED, TOKEN_REFRESHED

    Included Patches

    This milestone includes development patches v1.0.7-dev through v1.0.10-dev:

    • v1.0.7-dev: User CRUD with password hashing (initially BCrypt)
    • v1.0.8-dev: JWT infrastructure (JwtService, AuthenticationService)
    • v1.0.9-dev: Switch from BCrypt to Argon2id
    • v1.0.10-dev: JWT authentication filter and authorization enforcement

    Known Limitations

    • Single JWT secret for all tokens (consider key rotation in future)
    • No token revocation mechanism (tokens valid until expiration)
    • No password complexity requirements enforced (validation in future)
    • No rate limiting on login attempts (future enhancement)
    • No account lockout after failed login attempts (future enhancement)

    Next Steps

    The next milestone (v1.3.0) will focus on Model Providers, implementing:

    • Model provider registry and configuration
    • Ollama provider integration
    • OpenAI provider integration
    • Anthropic provider integration
    • Provider health checks and fallback mechanisms
    Downloads