Spring Security - Authentication Providers
Last Updated :
28 Apr, 2025
Authentication in Spring Security refers to the process of verifying the identity of a user or a client application attempting to access a protected resource. In other words, it's the process of validating the user's credentials (such as username and password) to ensure that they are who they claim to be. Spring Security provides various authentication mechanisms, such as form-based authentication, HTTP Basic authentication, and OAuth, among others. The authentication process typically involves collecting the user's credentials through a login form, validating them against a user database or authentication provider, and creating a security context that represents the authenticated user.
Importance of Authentication Providers in Spring Security
Authentication providers are an essential part of Spring Security as they play a critical role in verifying user credentials during the authentication process. Here are some of the key reasons why we need authentication providers:
- Verify user identity: Authentication providers are responsible for verifying the user's identity by checking their credentials, such as a username and password, against a known database or identity provider.
- Ensure security: Authentication providers help ensure the security of an application by preventing unauthorized access to sensitive resources. They do this by verifying that the user is who they claim to be and has the necessary permissions to access the requested resource.
- Support for multiple authentication mechanisms: Authentication providers can support multiple authentication mechanisms, such as username/password, biometrics, or multifactor authentication, to provide increased security and flexibility.
- Integration with external identity providers: Authentication providers can be integrated with external identity providers, such as LDAP, OAuth, or SAML, to provide a seamless and secure login experience for users.
Authentication Providers
Explanation of AuthenticationProvider interface:
- The AuthenticationProvider interface is a key component of Spring Security's authentication and authorization framework. It is responsible for authenticating a user's credentials and returning an Authentication object that represents the authenticated user. Here is an explanation of the key methods and responsibilities of the AuthenticationProvider interface:
- Authentication authenticate(Authentication authentication): This method takes an Authentication object as an argument and returns an Authentication object if the authentication is successful, otherwise, it throws an AuthenticationException. The Authentication object represents the authenticated identity of the user.
- boolean supports(Class<?> authentication): This method is used to check whether the AuthenticationProvider implementation supports the type of Authentication object that is passed to the authenticate() method. It returns true if the provider supports the authentication request, and false otherwise.
- The AuthenticationProvider interface is designed to support a wide range of authentication scenarios. For example, an implementation of this interface can perform the following actions:
- Check the user's credentials against a database or external identity providers, such as LDAP or OAuth.
- Perform additional validation of the user's credentials, such as checking for password expiration or account lockout.
- Assign user roles and permissions based on the user's credentials.
- Return additional information about the authenticated user, such as their full name or email address.
- Most common authentication providers in Spring Security:
- DaoAuthenticationProvider
- LdapAuthenticationProvider
- OpenIDAuthenticationProvider
- JwtAuthenticationProvider
- RememberMeAuthenticationProvider
1. DaoAuthenticationProvider
- DaoAuthenticationProvider is an authentication provider in Spring Security that is used to authenticate users stored in a database. It implements the AuthenticationProvider interface and can be used with any database that provides a JDBC driver.
- DaoAuthenticationProvider retrieves the user's credentials, such as username and password, from the database and compares them to the credentials provided by the user during login. If the credentials match, the provider creates an Authentication object representing the authenticated user.
- To use DaoAuthenticationProvider, you must provide a UserDetailsService implementation that retrieves user information from the database. UserDetailsService provides the username, password, and authorities for a given user. DaoAuthenticationProvider uses UserDetailsService to retrieve user information from the database during authentication.
- To use the DaoAuthenticationProvider, you need to configure it in your Spring Security configuration file.
Example:
Here's an example of how to configure the DaoAuthenticationProvider with an in-memory UserDetailsService and a BCryptPasswordEncoder:
1. First, you need to configure a DataSource bean to provide the database connection
Java
@Bean
public DataSource dataSource()
{
DriverManagerDataSource dataSource
= new DriverManagerDataSource();
dataSource.setDriverClassName("org.postgresql.Driver");
dataSource.setUrl(
"jdbc:postgresql://localhost:5432/mydatabase");
dataSource.setUsername("myuser");
dataSource.setPassword("mypassword");
return dataSource;
}
2. Next, you need to create a UserDetailsServicebean that will retrieve user information from the database. Here's an example implementation
Java
@Service
public class MyUserDetailsService implements UserDetailsService {
private final UserRepository userRepository;
public MyUserDetailsService(UserRepository userRepository) {
this.userRepository = userRepository;
}
@Override
public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
User user = userRepository.findByUsername(username);
if (user == null) {
throw new UsernameNotFoundException("User not found");
}
return new org.springframework.security.core.userdetails.User(
user.getUsername(),
user.getPassword(),
user.getRoles().stream().map(SimpleGrantedAuthority::new).collect(Collectors.toList())
);
}
}
3. Finally, you can configure DaoAuthenticationProvider in your SecurityConfig class
Java
@Configuration
@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter {
private final MyUserDetailsService userDetailsService;
private final PasswordEncoder passwordEncoder;
public SecurityConfig(MyUserDetailsService userDetailsService, PasswordEncoder passwordEncoder) {
this.userDetailsService = userDetailsService;
this.passwordEncoder = passwordEncoder;
}
@Bean
public DaoAuthenticationProvider authenticationProvider() {
DaoAuthenticationProvider provider = new DaoAuthenticationProvider();
provider.setUserDetailsService(userDetailsService);
provider.setPasswordEncoder(passwordEncoder);
return provider;
}
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.authenticationProvider(authenticationProvider());
}
@Override
protected void configure(HttpSecurity http) throws Exception {
http
.authorizeRequests()
.antMatchers("/admin/**").hasRole("ADMIN")
.antMatchers("/user/**").hasRole("USER")
.anyRequest().authenticated()
.and()
.formLogin()
.loginPage("/login")
.permitAll()
.and()
.logout()
.permitAll();
}
}
2. LdapAuthenticationProvider
- LdapAuthenticationProvider is a specific implementation of AuthenticationProvider that authenticates users against an LDAP (Lightweight Directory Access Protocol) server.
- LDAP is a protocol used for accessing and maintaining distributed directory information services over an Internet Protocol (IP) network. It is commonly used for managing user authentication and authorization information, such as usernames, passwords, and roles.
- The LdapAuthenticationProvider class in Spring Security provides an implementation of the AuthenticationProvider interface that delegates authentication to an LDAP server. It takes a LdapAuthenticator instance, which is responsible for performing the actual authentication against the LDAP server.
- To configure a LdapAuthenticationProviderin Spring Security, you need to provide the LdapAuthenticator and LdapAuthoritiesPopulatorobjects, as well as other optional settings such as the LDAP server URL, bind credentials, and search base.
Example:
Here's an example of how to configure LdapAuthenticationProvider in Spring Security.
1. Define the LdapContextSource bean to configure the connection to the LDAP server
Java
@Bean
public LdapContextSource contextSource() {
LdapContextSource contextSource = new LdapContextSource();
contextSource.setUrl("ldap://localhost:389");
contextSource.setBase("dc=example,dc=com");
contextSource.setUserDn("cn=admin,dc=example,dc=com");
contextSource.setPassword("password");
return contextSource;
}
2. Define the LdapUserSearch bean to configure how to search for a user in the LDAP server
Java
@Bean
public LdapUserSearch ldapUserSearch() {
return new FilterBasedLdapUserSearch("ou=users,dc=example,dc=com", "(uid={0})", contextSource());
}
3. Define the LdapAuthoritiesPopulator bean to configure how to retrieve the authorities for a user from the LDAP server
Java
@Bean
public LdapAuthoritiesPopulator authoritiesPopulator() {
return new DefaultLdapAuthoritiesPopulator(contextSource(), "ou=groups");
}
4. Define the LdapAuthenticationProvider bean that wraps all the previous beans and provides the authentication functionality:
Java
@Bean
public LdapAuthenticationProvider authenticationProvider() {
return new LdapAuthenticationProvider(ldapAuthenticator(), authoritiesPopulator());
}
5. Configure the AuthenticationManagerBuilder to use the LdapAuthenticationProvider bean
Java
@Autowired
public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
auth.authenticationProvider(authenticationProvider());
}
3. OpenIDAuthenticationProvider
- OpenIDAuthenticationProvider is a class in Spring Security that provides support for OpenID authentication. OpenID is an open standard for authentication that enables users to authenticate themselves to a website or application using an OpenID provider, such as Google or Facebook.
- In Spring Security, the OpenIDAuthenticationProvider is responsible for authenticating users based on OpenID authentication. It takes an OpenID4JavaConsumer instance, which is responsible for performing the actual authentication against the OpenID provider.
- To use OpenIDAuthenticationProvider, you need to configure an OpenID consumer and provider. The OpenID4JavaConsumer class handles the OpenID authentication flow and retrieves the user's information from the OpenID provider.
- You need to provide the OpenID4JavaConsumer with the following information:
- The OpenID provider URL: This is the URL of the OpenID provider that will be used to authenticate the user.
- The return URL: This is the URL that the OpenID provider will return the authentication response to after the user has been authenticated.
- The realm: This is a unique identifier for the relying party (your application) that is requesting authentication from the OpenID provider.
Example:
Here's an example of how to configure OpenIDAuthenticationProvider in Spring Security
1. First, configure an OpenID4JavaConsumer bean to handle the OpenID authentication flow and retrieve user information from the OpenID provider.
Java
@Bean
public OpenID4JavaConsumer openID4JavaConsumer() {
OpenID4JavaConsumer consumer = new OpenID4JavaConsumer();
consumer.setReturnToUrl(env.getProperty("security.openid.returnToUrl"));
consumer.setRealm(env.getProperty("security.openid.realm"));
consumer.setProviderUrl(env.getProperty("security.openid.providerUrl"));
return consumer;
}
2. Next, create an OpenIDAuthenticationProvider bean and configure it with the OpenID4JavaConsumer bean.
Java
@Bean
public OpenIDAuthenticationProvider openIDAuthenticationProvider() {
OpenIDAuthenticationProvider provider = new OpenIDAuthenticationProvider();
provider.setConsumer(openID4JavaConsumer());
return provider;
}
3. Add the OpenIDAuthenticationProvider to the AuthenticationManagerBuilder to handle OpenID authentication requests.
Java
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.authenticationProvider(openIDAuthenticationProvider());
}
4. Finally, configure the OpenIDAuthenticationFilter to intercept and handle OpenID authentication requests.
Java
@Override
protected void configure(HttpSecurity http) throws Exception {
http
// Other security configuration...
.addFilterAfter(openIDAuthenticationFilter(), AbstractPreAuthenticatedProcessingFilter.class)
// Other security configuration...
}
@Bean
public OpenIDAuthenticationFilter openIDAuthenticationFilter() {
OpenIDAuthenticationFilter filter = new OpenIDAuthenticationFilter();
filter.setConsumer(openID4JavaConsumer());
filter.setAuthenticationManager(authenticationManager());
filter.setAuthenticationSuccessHandler(openIDAuthenticationSuccessHandler());
filter.setAuthenticationFailureHandler(openIDAuthenticationFailureHandler());
return filter;
}
@Bean
public AuthenticationSuccessHandler openIDAuthenticationSuccessHandler() {
// Define a success handler to handle successful OpenID authentication
}
@Bean
public AuthenticationFailureHandler openIDAuthenticationFailureHandler() {
// Define a failure handler to handle failed OpenID authentication
}
4. JwtAuthenticationProvider
- JwtAuthenticationProvider is an implementation of the Spring Security AuthenticationProvider interface that is used to authenticate users based on JSON Web Tokens (JWTs).
- When a JWT is presented for authentication, the JwtAuthenticationProvider verifies the token's signature and extracts the user's identity information from the token. It then creates a JwtAuthenticationToken object, which encapsulates the authenticated user's details.
- To use JwtAuthenticationProvider in Spring Security, you will need to configure it with a JwtDecoder instance that will be used to decode the JWT. The JwtDecoder is responsible for verifying the signature and parsing the JWT payload.
Example:
Here's an example of how to configure JwtAuthenticationProvider in Spring Security:
1. First, configure a JwtDecoder bean that will be used to decode the JWT and verify its signature.
Java
@Bean
public JwtDecoder jwtDecoder() {
String secret = "mySecretKey";
return NimbusJwtDecoder.withSecretKey(new SecretKeySpec(secret.getBytes(), SignatureAlgorithm.HS256.getJcaName()))
.build();
}
2. Next, create a JwtAuthenticationProvider bean and configure it with the JwtDecoder bean.
Java
@Bean
public JwtAuthenticationProvider jwtAuthenticationProvider() {
return new JwtAuthenticationProvider(jwtDecoder());
}
3. Add the JwtAuthenticationProvider to the AuthenticationManagerBuilder to handle JWT authentication requests.
Java
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.authenticationProvider(jwtAuthenticationProvider());
}
4. Finally, configure the JwtAuthenticationFilter to intercept and handle JWT authentication requests.
Java
@Override
protected void configure(HttpSecurity http) throws Exception {
http
// Other security configuration...
.addFilterBefore(jwtAuthenticationFilter(), UsernamePasswordAuthenticationFilter.class)
// Other security configuration...
}
@Bean
public JwtAuthenticationFilter jwtAuthenticationFilter() {
JwtAuthenticationFilter filter = new JwtAuthenticationFilter();
filter.setAuthenticationManager(authenticationManager());
filter.setAuthenticationSuccessHandler(jwtAuthenticationSuccessHandler());
filter.setAuthenticationFailureHandler(jwtAuthenticationFailureHandler());
return filter;
}
@Bean
public AuthenticationSuccessHandler jwtAuthenticationSuccessHandler() {
// Define a success handler to handle successful JWT authentication
}
@Bean
public AuthenticationFailureHandler jwtAuthenticationFailureHandler() {
// Define a failure handler to handle failed JWT authentication
}
5. RememberMeAuthenticationProvider
- RememberMeAuthenticationProvider is an implementation of the Spring Security AuthenticationProvider interface that is used to authenticate users based on previously saved remember-me tokens.
- When a user logs in with the "remember me" option selected, Spring Security will issue a remember-me token and store it in a persistent storage, such as a database or a cookie. The next time the user visits the site, Spring Security will attempt to authenticate the user using the remember-me token. This is where RememberMeAuthenticationProvider comes into play.
- RememberMeAuthenticationProvider is responsible for validating the remember-me token and creating an Authentication object based on the token. If the token is valid, RememberMeAuthenticationProvider will create a new RememberMeAuthenticationToken and return it. If the token is not valid, RememberMeAuthenticationProvider will throw a BadCredentialsException.
- To use RememberMeAuthenticationProvider in Spring Security, you will need to configure it with a UserDetailsService that will be used to load the user's details based on the remember-me token.
Example:
Here's an example of how to configure RememberMeAuthenticationProvider in Spring Security:
1. Define a UserDetailsService implementation that retrieves user details from your application's database:
Java
@Service
public class UserDetailsServiceImpl implements UserDetailsService {
@Autowired
private UserRepository userRepository;
@Override
public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
User user = userRepository.findByUsername(username);
if (user == null) {
throw new UsernameNotFoundException("User not found with username: " + username);
}
return new org.springframework.security.core.userdetails.User(user.getUsername(), user.getPassword(),
Collections.singletonList(new SimpleGrantedAuthority(user.getRole().name())));
}
}
2. Configure authentication using the UserDetailsService implementation:
Java
@Configuration
@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter {
@Autowired
private UserDetailsService userDetailsService;
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.userDetailsService(userDetailsService);
}
// ...
}
3. Define a RememberMeAuthenticationProvider bean:
Java
@Bean
public RememberMeAuthenticationProvider rememberMeAuthenticationProvider() {
return new RememberMeAuthenticationProvider("myAppKey");
}
4. Define a PersistentTokenRepository implementation that stores remember-me tokens in your application's database:
Java
@Bean
public PersistentTokenRepository persistentTokenRepository() {
JdbcTokenRepositoryImpl tokenRepository = new JdbcTokenRepositoryImpl();
tokenRepository.setDataSource(dataSource); // configure DataSource
return tokenRepository;
}
5. Define a TokenBasedRememberMeServices bean that uses the RememberMeAuthenticationProvider and PersistentTokenRepository:
Java
@Bean
public TokenBasedRememberMeServices rememberMeServices() {
TokenBasedRememberMeServices rememberMeServices = new TokenBasedRememberMeServices("myAppKey", userDetailsService,
persistentTokenRepository());
rememberMeServices.setTokenValiditySeconds(604800); // one week
return rememberMeServices;
}
6. Configure remember-me authentication in your HttpSecurity configuration:
Java
@Override
protected void configure(HttpSecurity http) throws Exception {
http
.authorizeRequests()
.antMatchers("/public/**").permitAll()
.anyRequest().authenticated()
.and()
.formLogin()
.loginPage("/login")
.defaultSuccessUrl("/dashboard")
.and()
.rememberMe()
.key("myAppKey")
.rememberMeServices(rememberMeServices())
.and()
.logout()
.logoutUrl("/logout")
.logoutSuccessUrl("/public")
.and()
.exceptionHandling()
.accessDeniedPage("/403")
.and()
.csrf()
.disable();
}
Custom Authentication Provider
Explanation of how to create custom authentication and authorization providers:
- To create a custom authentication provider in Spring Security, you need to implement the AuthenticationProvider interface. The AuthenticationProvider interface has a single method authenticate(Authentication authentication) which takes an Authentication object as input and returns an Authentication object as output. The authenticate() method is responsible for authenticating the user based on the provided credentials and returning an Authentication object with the user's details.
- Here's a step-by-step guide on how to create a custom authentication provider in Spring Security:
1. Create a new class that implements the AuthenticationProvider interface.
Java
public class CustomAuthenticationProvider implements AuthenticationProvider {
@Override
public Authentication authenticate(Authentication authentication) throws AuthenticationException {
// TODO: Implement authentication logic
}
@Override
public boolean supports(Class<?> authentication) {
return authentication.equals(UsernamePasswordAuthenticationToken.class);
}
}
2. Implement the authenticate(Authentication authentication) method. This method takes an Authentication object as input and returns an Authentication object as output.
Java
public class CustomAuthenticationProvider implements AuthenticationProvider {
@Override
public Authentication authenticate(Authentication authentication) throws AuthenticationException {
String username = authentication.getName();
String password = authentication.getCredentials().toString();
// TODO: Implement authentication logic
List<GrantedAuthority> authorities = new ArrayList<>();
authorities.add(new SimpleGrantedAuthority("ROLE_USER"));
return new UsernamePasswordAuthenticationToken(username, password, authorities);
}
@Override
public boolean supports(Class<?> authentication) {
return authentication.equals(UsernamePasswordAuthenticationToken.class);
}
}
3. In the authenticate() method, implement the logic to authenticate the user based on the provided credentials. This can be done by querying a database or an external authentication service.
Java
public class CustomAuthenticationProvider implements AuthenticationProvider {
@Autowired
private UserService userService;
@Override
public Authentication authenticate(Authentication authentication) throws AuthenticationException {
String username = authentication.getName();
String password = authentication.getCredentials().toString();
User user = userService.findByUsername(username);
if (user == null || !password.equals(user.getPassword())) {
throw new BadCredentialsException("Invalid username or password");
}
List<GrantedAuthority> authorities = new ArrayList<>();
authorities.add(new SimpleGrantedAuthority("ROLE_USER"));
return new UsernamePasswordAuthenticationToken(username, password, authorities);
}
@Override
public boolean supports(Class<?> authentication) {
return authentication.equals(UsernamePasswordAuthenticationToken.class);
}
}
4. Implement the supports(Class<?> authentication) method. This method returns true if the authentication provider supports the specified authentication token class. In this example, we're only supporting the UsernamePasswordAuthenticationToken class.
Java
public class CustomAuthenticationProvider implements AuthenticationProvider {
@Autowired
private UserService userService;
@Override
public Authentication authenticate(Authentication authentication) throws AuthenticationException {
// TODO: Implement authentication logic
}
@Override
public boolean supports(Class<?> authentication) {
return authentication.equals(UsernamePasswordAuthenticationToken.class);
}
}
5. Inject the custom authentication provider into your AuthenticationManagerBuilder in your Spring Security configuration.
Java
@Configuration
@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter {
@Autowired
private CustomAuthenticationProvider customAuthenticationProvider;
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.authenticationProvider(customAuthenticationProvider);
}
// ...
}
Conclusion
- Spring Security provides a robust authentication and authorization framework for securing web applications. It includes a wide range of authentication providers, each with its own strengths and weaknesses, that can be used to authenticate users and grant them access to protected resources.
- The choice of authentication provider depends on the specific requirements of the application. For example, if the application needs to authenticate users against an LDAP directory, the LDAP authentication provider can be used. If the application requires social login functionality, the OAuth2 authentication provider can be used.
- In general, Spring Security provides a comprehensive set of authentication providers that can be used to secure different types of applications.
Similar Reads
Java Tutorial Java is a high-level, object-oriented programming language used to build web apps, mobile applications, and enterprise software systems. It is known for its Write Once, Run Anywhere capability, which means code written in Java can run on any device that supports the Java Virtual Machine (JVM).Java s
10 min read
Java Interview Questions and Answers Java is one of the most popular programming languages in the world, known for its versatility, portability, and wide range of applications. Java is the most used language in top companies such as Uber, Airbnb, Google, Netflix, Instagram, Spotify, Amazon, and many more because of its features and per
15+ min read
Java OOP(Object Oriented Programming) Concepts Java Object-Oriented Programming (OOPs) is a fundamental concept in Java that every developer must understand. It allows developers to structure code using classes and objects, making it more modular, reusable, and scalable.The core idea of OOPs is to bind data and the functions that operate on it,
13 min read
Arrays in Java Arrays in Java are one of the most fundamental data structures that allow us to store multiple values of the same type in a single variable. They are useful for storing and managing collections of data. Arrays in Java are objects, which makes them work differently from arrays in C/C++ in terms of me
15+ min read
Collections in Java Any group of individual objects that are represented as a single unit is known as a Java Collection of Objects. In Java, a separate framework named the "Collection Framework" has been defined in JDK 1.2 which holds all the Java Collection Classes and Interface in it. In Java, the Collection interfac
15+ min read
Inheritance in Java Java Inheritance is a fundamental concept in OOP(Object-Oriented Programming). It is the mechanism in Java by which one class is allowed to inherit the features(fields and methods) of another class. In Java, Inheritance means creating new classes based on existing ones. A class that inherits from an
13 min read
Java Exception Handling Exception handling in Java allows developers to manage runtime errors effectively by using mechanisms like try-catch block, finally block, throwing Exceptions, Custom Exception handling, etc. An Exception is an unwanted or unexpected event that occurs during the execution of a program, i.e., at runt
10 min read
Java Programs - Java Programming Examples In this article, we will learn and prepare for Interviews using Java Programming Examples. From basic Java programs like the Fibonacci series, Prime numbers, Factorial numbers, and Palindrome numbers to advanced Java programs.Java is one of the most popular programming languages today because of its
8 min read
Java Interface An Interface in Java programming language is defined as an abstract type used to specify the behaviour of a class. An interface in Java is a blueprint of a behaviour. A Java interface contains static constants and abstract methods. Key Properties of Interface:The interface in Java is a mechanism to
12 min read
Polymorphism in Java Polymorphism in Java is one of the core concepts in object-oriented programming (OOP) that allows objects to behave differently based on their specific class type. The word polymorphism means having many forms, and it comes from the Greek words poly (many) and morph (forms), this means one entity ca
7 min read