Issue
so I have this section of code in AppConfig.java:
@Configuration
@EnableWebSecurity
public class AppConfig extends WebSecurityConfigurerAdapter {
private final CurrentUserService currentUserService;
private final SessionFilter sessionFilter;
private final PasswordEncoder passwordEncoder;
@Autowired
@Lazy
public AppConfig(CurrentUserService currentUserService, SessionFilter sessionFilter, PasswordEncoder passwordEncoder) {
this.currentUserService = currentUserService;
this.sessionFilter = sessionFilter;
this.passwordEncoder = passwordEncoder;
}
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.userDetailsService(currentUserService).passwordEncoder(passwordEncoder);
}
@Override
protected void configure(HttpSecurity http) throws Exception {
http = http.cors().and().csrf().disable();
http = http.exceptionHandling().authenticationEntryPoint(
(request, response, authException) -> {
response.sendError(HttpServletResponse.SC_UNAUTHORIZED, authException.getMessage());
}
).and();
http.authorizeRequests().antMatchers("/api/login").permitAll().anyRequest().authenticated();
http.addFilterBefore(sessionFilter, UsernamePasswordAuthenticationFilter.class);
}
@Override
@Bean
public AuthenticationManager authenticationManagerBean() throws Exception {
return super.authenticationManagerBean();
}
@Bean
public BCryptPasswordEncoder passwordEncoder() {
return new BCryptPasswordEncoder();
}
}
if I get rid of the @Lazy it will not start, i have tried to get rid of the constructor and do:
@Autowired
private final CurrentUserService currentUserService;
@Autowired
private final SessionFilter sessionFilter;
@Autowired
private final PasswordEncoder passwordEncoder;
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.userDetailsService(currentUserService).passwordEncoder(passwordEncoder);
}
same thing, can someone please help me out, I really don't want to have to use the @Lazy Implementation. here is the error it returns:
Exception encountered during context initialization - cancelling refresh attempt: org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'appConfig' defined in file [C:\Users\Blade\Documents\WebMent\modules\backend\build\classes\java\main\com\shortsdesigns\webment\configuration\AppConfig.class]: Unsatisfied dependency expressed through constructor parameter 2; nested exception is org.springframework.beans.factory.BeanCurrentlyInCreationException: Error creating bean with name 'appConfig': Requested bean is currently in creation: Is there an unresolvable circular reference?
When getting rid of the constructor and using field injection it gives me this error:
Error creating bean with name 'appConfig': Unsatisfied dependency expressed through field 'passwordEncoder'; nested exception is org.springframework.beans.factory.BeanCurrentlyInCreationException: Error creating bean with name 'appConfig': Requested bean is currently in creation: Is there an unresolvable circular reference?
Solution
This error occurs because you're creating the PasswordEncoder
in the same class that you're injecting it.
The best solution is to not autowire the PasswordEncoder
(or the CurrentUserService
) at all.
It appears those instances are only used in the configure(AuthenticationManagerBuilder auth)
method, which is redundant.
Registering a PasswordEncoder
and UserDetailsService
as a bean is enough for Spring Security to detect them and use them in your configuration.
In other words, you should remove the following code:
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.userDetailsService(currentUserService).passwordEncoder(passwordEncoder);
}
The application will still behave in the exact same way.
Answered By - Eleftheria Stein-Kousathana
Answer Checked By - Senaida (JavaFixing Volunteer)