Home > Software design >  Spring Security Kotlin Field Injection of Repository Class Failing
Spring Security Kotlin Field Injection of Repository Class Failing

Time:10-28

I am new to Spring and Kotlin, and am trying to implement OAuth2 with a custom success handler. In the handler, I want to save the user details to my MongoDB database. Here is my security config (AuthenticationSuccessHandler is injected in the constructor):

@EnableWebSecurity
@Configuration
public class SecurityConfig(private val authenticationSuccessHandler : AuthenticationSuccessHandler) {
    @Throws(Exception::class)
    @Bean
    public fun override(http: HttpSecurity): SecurityFilterChain {
        return http
                .csrf{csrf -> csrf.disable()}
                .authorizeRequests{auth -> 
                    auth.antMatchers("/api/brackets").authenticated()
                    auth.antMatchers("/**").permitAll()
                }
                .oauth2Login()
                .successHandler(AuthenticationSuccessHandler())
                .and()
                .build()
    }
}

and here is my AuthenticationSuccessHandler class (see autowired userRepository):


@Component
public class AuthenticationSuccessHandler : SavedRequestAwareAuthenticationSuccessHandler() {

    private val redirectStrategy : RedirectStrategy = DefaultRedirectStrategy();
    private val logger : Logger = LoggerFactory.getLogger(javaClass)
    
    @Autowired
    private lateinit var userRepository : UserRepository
    
    @Throws(ServletException::class,IOException::class)
    override public fun onAuthenticationSuccess(request : HttpServletRequest, response : HttpServletResponse, authentication : Authentication)  {
        //if redirected from some specific url, need to remove the cachedRequest to force use defaultTargetUrl
        val requestCache : RequestCache = HttpSessionRequestCache();
        val savedRequest : SavedRequest = requestCache.getRequest(request, response);
        val userDetails : DefaultOidcUser = authentication.getPrincipal() as DefaultOidcUser
        logger.info(userDetails.getIdToken().getTokenValue())
        userRepository.save(User(userDetails.getName(), userDetails.getEmail(), AuthService.GOOGLE))
        redirectStrategy.sendRedirect(request, response, "/api/testAuth");
    }

}

Unfortunately when this handler is hit, the statement to save a new User fails with the message: "kotlin.UninitializedPropertyAccessException: lateinit property userRepository has not been initialized"

Any ideas why my userRepository is not being injected? Thank you so much!

CodePudding user response:

It looks like the problem is that I wasn't using my injected instance of authenticationSuccessHandler and instead instantiating a new one without use of the spring framework. I was able to fix this by changing .successHandler(AuthenticationSuccessHandler()) to .successHandler(authenticationSuccessHandler) that why the dependency injection worked

  • Related