How can I programmatically authenticate user with Spring Security using DaoAuthenticationProvider

被刻印的时光 ゝ 提交于 2019-12-07 00:13:38

问题


I was wondering what I am doing wrong here to authenticate a user. I have an application where the user goes through several steps to activate their account, and upon doing so I would like to bypass the login form and take them directly to their dashboard.

Here is what my automated login function looks like:

protected void automatedLogin(String username, String password, HttpServletRequest request) {

        try {
            // Must be called from request filtered by Spring Security, otherwise SecurityContextHolder is not updated
            CustomUserDetailsService udService = new CustomUserDetailsService(userDAO, request);
            UserDetails uDetails = udService.loadUserByUsername(username);
            UsernamePasswordAuthenticationToken token = new UsernamePasswordAuthenticationToken(uDetails, password);
            token.setDetails(new WebAuthenticationDetails(request));
            DaoAuthenticationProvider authenticator = new DaoAuthenticationProvider();
            Authentication authentication = authenticator.authenticate(token);
            SecurityContextHolder.getContext().setAuthentication(authentication);
        } catch (Exception e) {
            e.printStackTrace();
            SecurityContextHolder.getContext().setAuthentication(null);
        }

    }

I must use the DaoAuthenticationProvider class as my authentication provider. I have verified that I am getting a UserDetails model containing the correct credentials, ID, authority roles, etc.

When it calls the authenticate method I run into a Null Pointer somewhere along the way in the DaoAuthenticationProvider class:

org.springframework.security.authentication.AuthenticationServiceException at org.springframework.security.authentication.dao.DaoAuthenticationProvider.retrieveUser(DaoAuthenticationProvider.java:109) at org.springframework.security.authentication.dao.AbstractUserDetailsAuthenticationProvider.authenticate(AbstractUserDetailsAuthenticationProvider.java:132) at com.bosch.actions.BaseController.doAutoLogin(BaseController.java:659) . . . Caused by: java.lang.NullPointerException at org.springframework.security.authentication.dao.DaoAuthenticationProvider.retrieveUser(DaoAuthenticationProvider.java:101)

I'm really not sure what is null, as I don't have the source code available.

Edit I was able to find the source code here - https://github.com/SpringSource/spring-security/blob/master/core/src/main/java/org/springframework/security/authentication/dao/DaoAuthenticationProvider.java

I was able to get around the Null Pointer by explicitly setting the UserDetailsService on the object:

authenticator.setUserDetailsService(udService);

But now I get bad credentials exception when I know the password provided is correct, because I've seen it in the debugger in the UserDetails object set earlier in the code.

org.springframework.security.authentication.BadCredentialsException: Bad credentials at org.springframework.security.authentication.dao.DaoAuthenticationProvider.additionalAuthenticationChecks(DaoAuthenticationProvider.java:87) at org.springframework.security.authentication.dao.AbstractUserDetailsAuthenticationProvider.authenticate(AbstractUserDetailsAuthenticationProvider.java:149)


回答1:


I was able to get the authentication working by piecing together all of the properties defined in the spring bean definition and setting them programmatically on the DaoAuthenticationProvider object. Looking back this seems like it may have been a silly question, but I hope it helps someone!

Corrected Code:

protected void automatedLogin(String username, String password, HttpServletRequest request) {

        try {
            // Must be called from request filtered by Spring Security, otherwise SecurityContextHolder is not updated
            CustomUserDetailsService udService = new CustomUserDetailsService(userDAO, request);
            CustomMd5PasswordEncoder passEncoder = new CustomMd5PasswordEncoder();
            ReflectionSaltSource saltSource = new ReflectionSaltSource();
            saltSource.setUserPropertyToUse("salt");
            UsernamePasswordAuthenticationToken token = new UsernamePasswordAuthenticationToken(username, password);
            token.setDetails(new WebAuthenticationDetails(request));
            DaoAuthenticationProvider authenticator = new DaoAuthenticationProvider();
            authenticator.setUserDetailsService(udService);
            authenticator.setPasswordEncoder(passEncoder);
            authenticator.setSaltSource(saltSource);
            Authentication authentication = authenticator.authenticate(token);
            SecurityContextHolder.getContext().setAuthentication(authentication);
        } catch (Exception e) {
            e.printStackTrace();
            SecurityContextHolder.getContext().setAuthentication(null);
        }

    }


来源:https://stackoverflow.com/questions/18006137/how-can-i-programmatically-authenticate-user-with-spring-security-using-daoauthe

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!