
- Sprint Security - Home
- Spring Security - Introduction
- Spring Security - Architecture
- Spring Security - Project Modules
- Spring Security - Environment Setup
- Spring Security - Form Login
- Spring Security - Custom Form Login
- Spring Security - Logout
- Spring Security - Remember Me
- Spring Security - Redirection
- Spring Security - Taglibs
- Spring Security - XML Configuration
- Spring Security - Authentication Provider
- Spring Security - Basic Authentication
- Spring Security - AuthenticationFailureHandler
- Spring Security - JWT
- Spring Security - Retrieve User Information
- Spring Security - Maven
- Spring Security - Default Password Encoder
- Spring Security – Password Encoding
- Spring Security - Methods Level
- Spring Security - Manual Authentication
- Spring Security - Extra Login Fields
- Spring Security - Prevent Brute Force
- Spring Security - Login Page with React
- Spring Security - Security Filter Chain
- Spring Security - Securing Spring Boot API
- Spring Security Useful Resources
- Spring Security - Quick Guide
- Spring Security - Useful Resources
- Spring Security - Discussion
Spring Security - Retrieving User Information
Spring Security provides user information in SecurityContext once user is authenticated. We can retrieve user details in couple of ways. Let's discuss them one by one.
Using SecurityContextHolder
SecurityContextHolder provides static access to the security context and can be used to get the Authentication instance. Once Authentication instance is available, we can get the username easily as shown below:
Authentication authentication = SecurityContextHolder.getContext().getAuthentication(); String username = authentication.getName();
This approch is useful for any class to retrieve the user details and is not limited to controller classes.
Using Principal
We can use Principal as an argument to a controller class method which then can be used to get the name of the user as shown below:
@Controller public class AuthController { ... @GetMapping("/admin") public String admin(Principal principal) { String username = principal.getName(); System.out.println("AuthController.admin()::Username: " + username); ... }
Using Authetication
We can use Authentication as an argument to a controller class method which then can be used to get the name of the user and role as shown below:
@Controller public class AuthController { ... @GetMapping("/admin") public String admin(Authentication authentication) { String username = authentication.getName(); System.out.println("AuthController.admin()::Username: " + username); UserDetails userDetails = (UserDetails) authentication.getPrincipal(); System.out.println("User Role: " + userDetails.getAuthorities()); ... }
Using HttpServletRequest
We can use HttpServletRequest as an argument to a controller class method to get the UserPrincipal which then can be used to get the name of the user as shown below:
@Controller public class AuthController { ... @GetMapping("/admin") public String admin(HttpServletRequest request) { Principal principal = request.getUserPrincipal(); String username = principal.getName(); System.out.println("AuthController.admin()::Username: " + username); ... }
Using @AuthenticationPrincipal to inject UserDetails
We can use @AuthenticationPrincipal annotation in a controller class method to get the UserDetails which then can be used to get the name of the user as shown below:
@Controller public class AuthController { ... @GetMapping("/admin") public String admin(@AuthenticationPrincipal UserDetails userDetails) { String username = userDetails.getUsername(); System.out.println("AuthController.admin()::Username: " + username); ... }
Using Thymeleaf templating engine
Thymeleaf is a server side web templating engine and provides an easy integration with Spring MVC. We can specify authentication tag to get the username as shown below:
<!DOCTYPE html> <html xmlns="http://www.w3.org/1999/xhtml" xmlns:th="https://www.thymeleaf.org" xmlns:sec="https://www.thymeleaf.org/thymeleaf-extras-springsecurity6"> ... <h1 th:inline="text">Hello <span sec:authentication="name"></span>!</h1> ... <html>
We need to add following thymeleaf spring dependencies to integrate thymeleaf with Spring security.
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-thymeleaf</artifactId> </dependency> <dependency> <groupId>org.thymeleaf.extras</groupId> <artifactId>thymeleaf-extras-springsecurity6</artifactId> </dependency>
Now let's see various options with following complete code in action.
Before you start writing your first example using Spring framework, you have to make sure that you have set up your Spring environment properly as explained in Spring Security - Environment Setup Chapter. We also assume that you have a bit of working knowledge on Spring Tool Suite IDE.
Now let us proceed to write a Spring MVC based Application managed by Maven, which will ask user to login, authenticate user and then provide option to logout using Spring Security Form Login Feature.
Create Project using Spring Initializr
Spring Initializr is great way to start with Spring Boot project. It provides a easy to use User Interface to create a project, add dependencies, select java runtime etc. It generates a skeleton project structure which once downloaded can be imported in spring tool suite and we can proceed with our readymade project structure.
We're choosing a maven project, naming the project as formlogin, with java version as 21. Following dependencies are added:
Spring Web
Spring Security
Spring Boot DevTools

Thymeleaf is a templating engine for Java. It allows us to quickly develop static or dynamic web pages for rendering in the browser. It is extremely extensible and allows us to define and customize the processing of our templates in fine detail. In addition to this, we can learn more about Thymeleaf by clicking this link.
Let's move on to generate our project and download it. We then extract it to a folder of our choice and use any IDE to open it. I shall be using Spring Tools Suite 4. It is available for free downloading from the https://spring.io/tools website and is optimized for spring applications.
pom.xml with all relevant dependencies
Let's take a look at our pom.xml file. It should look something similar to this −
pom.xml
<?xml version="1.0" encoding="UTF-8"?> <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd"> <modelVersion>4.0.0</modelVersion> <parent> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-parent</artifactId> <version>3.3.1</version> <relativePath/> <!-- lookup parent from repository --> </parent> <groupId>com.tutorialspoint.security</groupId> <artifactId>formlogin</artifactId> <version>0.0.1-SNAPSHOT</version> <name>formlogin</name> <description>Demo project for Spring Boot</description> <url/> <licenses> <license/> </licenses> <developers> <developer/> </developers> <scm> <connection/> <developerConnection/> <tag/> <url/> </scm> <properties> <java.version>21</java.version> </properties> <dependencies> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-security</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-thymeleaf</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> <dependency> <groupId>org.thymeleaf.extras</groupId> <artifactId>thymeleaf-extras-springsecurity6</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-devtools</artifactId> <scope>runtime</scope> <optional>true</optional> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-test</artifactId> <scope>test</scope> </dependency> <dependency> <groupId>org.springframework.security</groupId> <artifactId>spring-security-test</artifactId> <scope>test</scope> </dependency> </dependencies> <build> <plugins> <plugin> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-maven-plugin</artifactId> </plugin> </plugins> </build> </project>
Spring Security Configuration Class
Inside of our config package, we have created the WebSecurityConfig class. We shall be using this class for our security configurations, so let's annotate it with an @Configuration annotation and @EnableWebSecurity. As a result, Spring Security knows to treat this class a configuration class. As we can see, configuring applications have been made very easy by Spring.
WebSecurityConfig
package com.tutorialspoint.security.formlogin.config; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.security.config.annotation.web.builders.HttpSecurity; import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity; import org.springframework.security.config.annotation.web.configurers.AbstractHttpConfigurer; import org.springframework.security.core.userdetails.User; import org.springframework.security.core.userdetails.UserDetails; import org.springframework.security.core.userdetails.UserDetailsService; import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder; import org.springframework.security.crypto.password.PasswordEncoder; import org.springframework.security.provisioning.InMemoryUserDetailsManager; import org.springframework.security.web.SecurityFilterChain; @Configuration @EnableWebSecurity public class WebSecurityConfig { @Bean protected UserDetailsService userDetailsService() { UserDetails user = User.builder() .username("user") .password(passwordEncoder().encode("user123")) .roles("USER") .build(); UserDetails admin = User.builder() .username("admin") .password(passwordEncoder().encode("admin123")) .roles("USER", "ADMIN") .build(); return new InMemoryUserDetailsManager(user, admin); } @Bean protected PasswordEncoder passwordEncoder() { return new BCryptPasswordEncoder(); } @Bean protected SecurityFilterChain filterChain(HttpSecurity http) throws Exception { return http .csrf(AbstractHttpConfigurer::disable) .authorizeHttpRequests( request -> request.requestMatchers("/login").permitAll() .requestMatchers("/**").authenticated() ) .formLogin(form -> form.loginPage("/login") .defaultSuccessUrl("/") .failureUrl("/login?error=true") .permitAll()) .logout(config -> config .logoutUrl("/logout") .logoutSuccessUrl("/login")) .build(); } }
Controller Class
In this class, we've created a mapping for multiple endpoints for the index, login, admin pages of this application.
AuthController
package com.tutorialspoint.security.formlogin.controllers; import java.security.Principal; import org.springframework.security.core.Authentication; import org.springframework.security.core.annotation.AuthenticationPrincipal; import org.springframework.security.core.context.SecurityContextHolder; import org.springframework.security.core.userdetails.UserDetails; import org.springframework.stereotype.Controller; import org.springframework.web.bind.annotation.GetMapping; import jakarta.servlet.http.HttpServletRequest; @Controller public class AuthController { @GetMapping("/") public String home(Authentication authentication, HttpServletRequest request) { // get username from Authetication instance String username = authentication.getName(); System.out.println("AuthController.home()::Username: " + username); // get principal instance from Authentication instance to get user role UserDetails userDetails = (UserDetails) authentication.getPrincipal(); System.out.println("User Role: " + userDetails.getAuthorities()); // get principal instance from HTTP Request Principal principal = request.getUserPrincipal(); // get username username = principal.getName(); System.out.println("AuthController.home()::principal.getName(): " + username); return "index"; } @GetMapping("/login") public String login() { return "login"; } @GetMapping("/user") public String user() { // get authentication instance from Security Context Authentication authentication = SecurityContextHolder.getContext().getAuthentication(); // get the user name String username = authentication.getName(); System.out.println("AuthController.user()::Username: " + username); return "user"; } @GetMapping("/admin") public String admin(Principal principal, @AuthenticationPrincipal UserDetails userDetails) { // get the username from principal instance String username = principal.getName(); System.out.println("AuthController.admin()::Username: " + username); // get the username from userdetails instance username = userDetails.getUsername(); System.out.println("AuthController.admin()::userDetails.getUsername(): " + username); return "admin"; } }
Views
Create index.html in /src/main/resources/templates folder with following content to act as a home page.
index.html
<!DOCTYPE html> <html xmlns="http://www.w3.org/1999/xhtml" xmlns:th="https://www.thymeleaf.org" xmlns:sec="https://www.thymeleaf.org/thymeleaf-extras-springsecurity6"> <head> <title> Hello World! </title> </head> <body> <h1 th:inline="text">Hello World!</h1> <a href="/logout" alt="logout">Sign Out</a> </body> <html>
Create user.html in /src/main/resources/templates folder with following content to act as user page.
user.html
<!DOCTYPE html> <html xmlns="http://www.w3.org/1999/xhtml" xmlns:th="https://www.thymeleaf.org" xmlns:sec="https://www.thymeleaf.org/thymeleaf-extras-springsecurity6"> <head> <title> Hello User! </title> </head> <body> <p>User Dashboard</p> <h1 th:inline="text">Hello <span sec:authentication="name"></span>!</h1> <a href="/logout" alt="logout">Sign Out</a> </body> <html>
Create admin.html in /src/main/resources/templates folder with following content to act as admin page.
admin.html
<!DOCTYPE html> <html xmlns="http://www.w3.org/1999/xhtml" xmlns:th="https://www.thymeleaf.org" xmlns:sec="https://www.thymeleaf.org/thymeleaf-extras-springsecurity6"> <head> <title> Hello User! </title> </head> <body> <p>User Dashboard</p> <h1 th:inline="text">Hello <span sec:authentication="name"></span>!</h1> <a href="/logout" alt="logout">Sign Out</a> </body> <html>
Running the Application
As we've all component ready, let's run the Application. Right Click on the project, select Run As and then Spring Boot App.
It will boot up the application and once application is started, we can run localhost:8080 to check the changes.
Output
Now open localhost:8080, you can see the login page.

Home Page

Check the logs for Home Page
Now check the application logs. It will have following entries apart from Spring boot logs:
AuthController.home()::Username: user User Role: [ROLE_USER] AuthController.home()::principal.getName(): user
User Page
Now open localhost:8080/user, you can check the following logs in application logs.
AuthController.user()::Username: user
You can check the username being shown in html as well.

Admin Page
Now open localhost:8080/admin, you can check the following logs in application logs.
AuthController.admin()::Username: user AuthController.admin()::userDetails.getUsername(): user