Я меняю существующее приложение с пружинной загрузкой, это приложение не использует Spring Security для аутентификации, аутентификация - это метод в контроллере, поэтому я хочу использовать Spring Security и я пытаюсь использовать ручную аутентификацию в Spring Securityно не работает, ниже вы можете увидеть код:
Контроллер:
@Autowired
@Qualifier(BeanIds.AUTHENTICATION_MANAGER)
private AuthenticationManager authenticationManager;
@PostMapping(value = "/authenticate")
public ResponseEntity<UsuarioRequest> login(@RequestBody UsuarioRequest request, HttpServletRequest servletRequest)
throws AppException {
UsernamePasswordAuthenticationToken authToken = new UsernamePasswordAuthenticationToken(request.getUsulog(), request.getUsupass());
Authentication authentication = authenticationManager
.authenticate(authToken);
SecurityContext context = SecurityContextHolder.getContext();
context.setAuthentication(authentication);
UsuarioRequest usuario = usuarioFacadeAPI.findByUsername(request.getUsulog());
return new ResponseEntity<UsuarioRequest>(usuario, HttpStatus.OK);
}
Конфигурация безопасности:
@Configuration
@EnableWebSecurity
@EnableGlobalMethodSecurity(prePostEnabled = true, securedEnabled = true)
public class SecurityConfig extends WebSecurityConfigurerAdapter {
private SiscoAuthenticationProvider siscoAuthenticationProvider;
@Autowired
public SecurityConfig(SiscoAuthenticationProvider siscoAuthenticationProvider) {
super();
this.siscoAuthenticationProvider = siscoAuthenticationProvider;
}
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.authenticationProvider(siscoAuthenticationProvider);
}
@Override
protected void configure(HttpSecurity http) throws Exception {
http.formLogin().disable();
http.csrf().disable();
http.authenticationProvider(siscoAuthenticationProvider).authorizeRequests()
.antMatchers("/login/api/**", "/zona/api/**", "/rol/api/**").permitAll()
.anyRequest().authenticated();
}
@Bean(name = BeanIds.AUTHENTICATION_MANAGER)
@Override
protected AuthenticationManager authenticationManager() throws Exception {
return super.authenticationManager();
}
}
CustomAuthenticationProvider:
@Component
public class SiscoAuthenticationProvider implements AuthenticationProvider{
private static final String ROLE = "ROLE_";
@Autowired
private UsuarioServiceAPI usuarioServiceAPI;
@Override
public Authentication authenticate(Authentication authentication) throws AuthenticationException {
UsernamePasswordAuthenticationToken token = null;
try {
UsuarioRequest request = usuarioServiceAPI.authenticate(authentication.getPrincipal().toString(), authentication.getCredentials().toString());
List<RolRequest> rols = request.getRoles();
List<SimpleGrantedAuthority> authorities = new ArrayList<>();
for (RolRequest rol : rols) {
authorities.add(new SimpleGrantedAuthority(ROLE+rol.getRolnom()));
}
token = new UsernamePasswordAuthenticationToken(authentication.getPrincipal(), authentication.getCredentials(), authorities);
} catch (AppException e) {
String message = BundleLoader.getMessage(e.getDetails().getBundle(), e.getDetails().getKey(),
LocaleContextHolder.getLocale());
throw new UsernameNotFoundException(message, e);
}
return token;
}
@Override
public boolean supports(Class<?> authentication) {
return UsernamePasswordAuthenticationToken.class.isAssignableFrom(authentication);
}
}
Для конфигурации allowAll проблем не возникало, но любой другой запрос возвращает код ошибки 403 даже после успешной аутентификации, я подозреваю, что в контроллере SecurityContextHolder не обновляет аутентификацию, поэтому пользователь всегда является анонимным.