Appearance
Spring Boot Security (Part 4) | Basic Authentication and Stateless Security
The Building Keycode Passphrase Analogy
Imagine a shared office workspace. There is no front desk receptionist taking names, stamping badges, or filing paperwork. Above the heavy glass door sits a simple numeric keypad. Every time a member wants to enter the building — whether in the morning, after lunch, or at midnight — they punch in their secret four digit code on the keypad. The electronic lock evaluates the code instantaneously. If the code is correct, the lock disengages for two seconds. Once you are inside, the keypad immediately forgets that you entered. When you leave to buy a coffee and return ten minutes later, you must punch in the exact same keycode again.
In HTTP web communications, HTTP Basic Authentication is that numeric keypad. There are no server side sessions, no login forms, and no cookies. On every single HTTP request, the client includes an Authorization header containing the username and password encoded in Base64. The server validates the credentials on the fly, processes the request, and stores zero session state in memory.
This lecture covers HTTP Basic Authentication standards (RFC 7617), configuring httpBasic() in Spring Security, stateless session policy (SessionCreationPolicy.STATELESS), machine to machine API use cases, and security vulnerabilities when used over unencrypted channels.
How HTTP Basic Authentication Works
HTTP Basic Authentication is a native standard defined in RFC 7617:
[ Client ] [ Spring Boot Server ]
| |
| --- 1. GET /api/orders (No Credentials) ------------------------> |
| | Rejects unauthenticated call
| <-- 2. HTTP 401 Unauthorized ------------------------------------ |
| WWW-Authenticate: Basic realm="Realm" |
| |
| --- 3. GET /api/orders -----------------------------------------> |
| Authorization: Basic YWxpY2U6c2VjcmV0MTIz |
| | Decodes Base64 -> "alice:secret123"
| | Authenticates credentials
| <-- 4. HTTP 200 OK (Orders JSON) -------------------------------- |The Structure of the Authorization Header:
- Concatenate username and password with a colon:
alice:secret123. - Encode the string using standard Base64:
Base64("alice:secret123") = "YWxpY2U6c2VjcmV0MTIz". - Prepend the word
Basicand a space:Authorization: Basic YWxpY2U6c2VjcmV0MTIz.
Configuring Basic Authentication in Spring Boot 3
Configure httpBasic() on your SecurityFilterChain:
java
package com.example.orderservice.config;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.Customizer;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.http.SessionCreationPolicy;
import org.springframework.security.web.SecurityFilterChain;
@Configuration
@EnableWebSecurity
public class BasicAuthSecurityConfig {
@Bean
public SecurityFilterChain securityFilterChain(HttpSecurity http) throws Exception {
http
// 1. Disable CSRF (Stateless REST APIs using Basic Auth are immune to CSRF)
.csrf(csrf -> csrf.disable())
// 2. Configure Stateless Session Creation Policy
.sessionManagement(session -> session
.sessionCreationPolicy(SessionCreationPolicy.STATELESS)
)
// 3. Define authorization rules
.authorizeHttpRequests(auth -> auth
.requestMatchers("/public/**").permitAll()
.requestMatchers("/api/admin/**").hasRole("ADMIN")
.anyRequest().authenticated()
)
// 4. Enable HTTP Basic Authentication
.httpBasic(Customizer.withDefaults());
return http.build();
}
}Critical Tuning: SessionCreationPolicy.STATELESS
By default, even when using Basic Auth, Spring Security will attempt to create an HttpSession after the first successful authentication so subsequent calls can reuse the session cookie.
For true REST APIs, you must explicitly configure: sessionCreationPolicy(SessionCreationPolicy.STATELESS).
This instructs Spring Security to never create an HttpSession and never read from one. The client is forced to provide the Authorization header on every request, delivering complete statelessness.
When to Use Basic Authentication
Basic Authentication is not designed for public consumer facing single page apps or mobile applications. However, it remains widely used in specific scenarios:
Recommended Use Cases:
- Machine to Machine Internal Communication: Automated batch daemons, cron jobs, or private microservices communicating across a private virtual cloud.
- Monitoring and Health Scrapers: Prometheus scrapers or internal monitoring agents polling
/actuator/metrics. - Developer Prototyping: Quick API testing using
curlor Postman during early development phases.
Why Basic Auth Is Avoided for End Users:
- No Native Logout: Browsers cache Basic Auth credentials in memory until the entire browser process is closed. There is no standard HTTP mechanism for a server to instruct a browser to forget Basic Auth credentials.
- Credential Exposure: Because the client transmits the raw username and password on every single HTTP exchange, any compromised connection compromises the user's permanent master password.
Testing Basic Auth via cURL and RestTemplate
Testing with cURL:
bash
# Using -u flag (cURL automatically base64 encodes username:password)
curl -u alice:secret123 http://localhost:8080/api/orders
# Or manually passing header:
curl -H "Authorization: Basic YWxpY2U6c2VjcmV0MTIz" http://localhost:8080/api/ordersCalling from Java RestTemplate:
java
HttpHeaders headers = new HttpHeaders();
headers.setBasicAuth("alice", "secret123");
HttpEntity<Void> request = new HttpEntity<>(headers);
ResponseEntity<String> response = restTemplate.exchange(
"http://localhost:8080/api/orders",
HttpMethod.GET,
request,
String.class
);Security Requirements: Mandatory HTTPS
Base64 is NOT encryption. Base64 is merely an open encoding scheme designed to safely transmit binary data across text protocols. Anyone who intercepts a plain HTTP Basic Auth header can decode it in one millisecond:
bash
echo "YWxpY2U6c2VjcmV0MTIz" | base64 --decode
# Prints: alice:secret123Therefore, Basic Authentication must strictly be deployed over TLS/HTTPS in production environments. Over HTTPS, the entire HTTP exchange — including all request headers — is encrypted with asymmetric TLS cryptography, preventing packet sniffing and man in the middle attacks.
Interview Questions & Pitfalls
Q1: What is the structure of the Authorization header in HTTP Basic Authentication?
The header consists of the keyword Basic followed by a space and a Base64 encoded string representing the username and password concatenated with a colon: Authorization: Basic Base64(username:password).
Q2: Why is Base64 encoding in Basic Authentication not considered secure on its own?
Base64 is a reversible encoding algorithm, not an encryption algorithm. Anyone who intercepts the HTTP header can instantly decode the original plain text credentials. Basic Authentication is only secure when transmitted over an encrypted HTTPS connection.
Q3: What is the effect of configuring SessionCreationPolicy.STATELESS in Spring Security?
It guarantees that Spring Security will never create an HttpSession in memory and will never inspect session cookies. Every incoming request must provide its own credentials in the Authorization header, ensuring true statelessness across requests.
Q4: Why is implementing user logout difficult when using Basic Authentication in web browsers?
Browsers automatically cache Basic Authentication credentials in process memory and re transmit them on every subsequent request to that domain. Because there is no server side session to destroy and no standardized HTTP command to force a browser to clear cached basic credentials, logging out typically requires closing the browser window or returning a 401 Unauthorized with a bogus realm to trick the browser.
Q5: Why is CSRF protection usually disabled for stateless REST APIs using Basic Authentication?
CSRF attacks rely on the browser automatically attaching ambient authentication credentials (such as session cookies) to cross domain requests. In stateless APIs where authentication relies strictly on explicit Authorization: Basic ... headers that browsers do not attach automatically to foreign domain requests, CSRF vulnerabilities do not exist, allowing CSRF protection to be safely disabled.