j_spring_security_check - spring security java
¿Cómo iniciar sesión automáticamente como usuario utilizando Spring Security sin conocer su contraseña? (3)
Mi aplicación usa Spring Security y mi cliente requiere:
- usuarios para poder iniciar sesión automáticamente después del registro.
- un administrador para iniciar sesión como cualquier usuario sin conocer su contraseña.
Así que tengo que averiguar cómo iniciar sesión como cualquier usuario automáticamente sin conocer su contraseña.
¿Cómo se puede lograr esto utilizando Spring Security?
Para que esto funcione, tuve que:
Configure una referencia al UserDetailsService (jdbcUserService)
<authentication-manager>
<authentication-provider>
<jdbc-user-service id="jdbcUserService" data-source-ref="dataSource"
users-by-username-query="select username,password, enabled from users where username=?"
authorities-by-username-query="select u.username, ur.authority from users u, user_roles ur where u.user_id = ur.user_id and u.username =? "
/>
</authentication-provider>
</authentication-manager>
Autocablee mi userDetailsManager en mi controlador:
@Autowired
@Qualifier("jdbcUserService") // <-- this references the bean id
public UserDetailsManager userDetailsManager;
En el mismo controlador, autentica a mi usuario así:
@RequestMapping("/automatic/login/test")
public @ResponseBody String automaticLoginTest(HttpServletRequest request)
{
String username = "[email protected]";
Boolean result = authenticateUserAndInitializeSessionByUsername(username, userDetailsManager, request);
return result.toString();
}
public boolean authenticateUserAndInitializeSessionByUsername(String username, UserDetailsManager userDetailsManager, HttpServletRequest request)
{
boolean result = true;
try
{
// generate session if one doesn''t exist
request.getSession();
// Authenticate the user
UserDetails user = userDetailsManager.loadUserByUsername(username);
Authentication auth = new UsernamePasswordAuthenticationToken(user, null, user.getAuthorities());
SecurityContextHolder.getContext().setAuthentication(auth);
}
catch (Exception e)
{
System.out.println(e.getMessage());
result = false;
}
return result;
}
Tenga en cuenta que aquí puede encontrar un buen precursor para simplemente usar la seguridad de primavera para su aplicación.
Esta es la respuesta a la pregunta anterior en Controlador:
@RequestMapping(value = "/registerHere", method = RequestMethod.POST)
public ModelAndView registerUser(@ModelAttribute("user") Users user, BindingResult result,
HttpServletRequest request, HttpServletResponse response) {
System.out.println("register 3");
ModelAndView mv = new ModelAndView("/home");
mv.addObject("homePagee", "true");
String uname = user.getUsername();
if (userDAO.getUserByName(uname) == null) {
String passwordFromForm = user.getPassword();
userDAO.saveOrUpdate(user);
try {
authenticateUserAndSetSession(user, passwordFromForm, request);
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
System.out.println("register 4");
log.debug("Ending of the method registerUser");
return mv;
}
El método anterior adicional en el controlador se define como:
`private void authenticateUserAndSetSession(Users user, String passwor`dFromForm, HttpServletRequest request){
String username = user.getUsername();
System.out.println("username: " + username + " password: " + passwordFromForm);
UserDetails userDetails = userDetailsService.loadUserByUsername(user.getUsername());
UsernamePasswordAuthenticationToken usernamePasswordAuthenticationToken = new UsernamePasswordAuthenticationToken(username, passwordFromForm, userDetails.getAuthorities());
request.getSession();
System.out.println("Line Authentication 1");
usernamePasswordAuthenticationToken.setDetails(new WebAuthenticationDetails(request));
System.out.println("Line Authentication 2");
Authentication authenticatedUser = authenticationManager.authenticate(usernamePasswordAuthenticationToken);
System.out.println("Line Authentication 3");
if (usernamePasswordAuthenticationToken.isAuthenticated()) {
SecurityContextHolder.getContext().setAuthentication(authenticatedUser);
System.out.println("Line Authentication 4");
}
request.getSession().setAttribute(HttpSessionSecurityContextRepository.SPRING_SECURITY_CONTEXT_KEY, SecurityContextHolder.getContext());// creates context for that session.
System.out.println("Line Authentication 5");
session.setAttribute("username", user.getUsername());
System.out.println("Line Authentication 6");
session.setAttribute("authorities", usernamePasswordAuthenticationToken.getAuthorities());
System.out.println("username: " + user.getUsername() + "password: " + user.getPassword()+"authorities: "+ usernamePasswordAuthenticationToken.getAuthorities());
user = userDAO.validate(user.getUsername(), user.getPassword());
log.debug("You are successfully register");
}
Otras respuestas no sugirieron ponerlo en try / catch para que uno no se dé cuenta de por qué la lógica no funciona mientras se ejecuta el código ... y no hay nada ni error ni excepción en la consola. Entonces, si no lo pones en try catch, no obtendrás excepción de malas credenciales.