Two or more authentication-manager in Spring security

By W.ZH Sept 2016

In Spring Security, you may need to two separate authentication-manager in system.  here is one example :

    <!-- Authentication manager 1 -->
    <security:authentication-manager id="userAuthenManager">
        <security:authentication-provider
            user-service-ref="userDetailsService">
            <security:password-encoder hash="md5" />
        </security:authentication-provider>
    </security:authentication-manager>
  
    <bean id="userDetailsService" class="com.abc.userdetails.UserDetailsServiceImpl" />

    <!-- Authentication manager 2 -->
    <security:authentication-manager id="dummyAuthenManager"> 
        <security:authentication-provider> 
            <security:user-service> 
                <security:user name="admin_user" password="password" authorities="ROLE_ADMIN" /> 
                <security:user name="normal_user" password="password" authorities="ROLE_USER" /> 
            </security:user-service> 
        </security:authentication-provider> 
    </security:authentication-manager>

 

So there is some special note you need to notice at here:

  1. Two or more authentication-manager must have respectively unique ID for them. So  that when you define the http security checker, you can use ID to define which authentication-manager is used. Like this:
    <security:http auto-config="true" use-expressions="true"
            authentication-manager-ref="userAuthenManager">
              。。。。。。。。。。。。。。。。。。。
        </security:http>
  2.  Order and others no special request.
  3. Normally when you create a authentication-manager, you must have have the user service  for it. they will have different user details service for it.
  4. To create a user service, you can use the dummy user hard code there(for testing only), like the dummyAuthenManager. or you can use a JDBC access the user details from DB tables. or you can implement a user service by your self by implement interface of org.springframework.security.core.userdetails.UserDetailsService, such as the UserDetailsServiceImpl in my example.  The jave code will like this in my example:

 

package com.abc.userdetails;

import javax.annotation.Resource;

import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.stereotype.Service;

import com.abc.dbservice.impl.UserInfoServiceImpl;

@Service
public class UserDetailsServiceImpl implements UserDetailsService {

    @Resource(name = "userInfoService")
    private UserInfoServiceImpl userInfoService;
    @Override
    public UserDetails loadUserByUsername(String username)
            throws UsernameNotFoundException {
        UserDetails user = userInfoService.searchByLoginId(username);
        if (user == null) {
            throw new UsernameNotFoundException(String.format(
                    "No user found with username '%s'.", username));
        } else {
            return user;
        }
    }
}

loadUserByUsername method is the only one you need to realize for this interface. and authentication-manager will call this method to get user, and then compare it with the user’s input name and password to do the authentication.

Implement the UserDetailsService inteface should be the best way for the user service as you can do a lot things in the UserDetailsServiceImpl code.

 

 

 

Advertisements