如何使用 Spring Security 3.1 以编程方式登录用户
Posted
技术标签:
【中文标题】如何使用 Spring Security 3.1 以编程方式登录用户【英文标题】:How to programmatically log user in with Spring Security 3.1 【发布时间】:2011-11-28 16:42:47 【问题描述】:在 Spring 和 Spring Security 3.1 中以特定用户名以编程方式登录 Web 访问者的正确方法是什么?看来我在 2.5 下的操作方式发生了一些变化。我确信现在有更好的方法来做到这一点。
基本上,当我创建一个新用户时,我还需要同时登录。
【问题讨论】:
【参考方案1】:创建一个Authentication
(通常是UsernamePasswordAuthenticationToken
)然后调用
SecurityContextHolder.getContext().setAuthentication(authentication)
【讨论】:
并将 UsernamePasswordAuthenticationToken 的密码设置为空字符串?对于我必须想象的如此普遍需要的东西来说,这似乎太不优雅了。现在有什么 webapp 在注册时不会自动登录?至少权限有限... 然后实现自己的Authentication,或者子类AbstractAuthenticationToken。 很好奇为什么还没有一种简单的,甚至是声明式的方式来以编程方式让人们登录?至少一个无密码的 AuthenticationToken .. 你不必使用空字符串,你可以使用他们注册的密码。 我想对于新用户注册的具体情况是有道理的,但与大多数网站一样,我不存储明文密码,即使我这样做也是不必要的查找。【参考方案2】:这三行代码为我完成了工作:
Authentication request = new UsernamePasswordAuthenticationToken( username, password );
Authentication result = authenticationManager.authenticate( request );
SecurityContextHolder.getContext().setAuthentication( result );
【讨论】:
我正在寻找一种以同样优雅的方式添加记住我功能的方法.... 你找到了记住我的解决方案吗? 这可能有解决方案:***.com/questions/7806921/…【参考方案3】:如果您有兴趣这样做以进行测试,您可以这样做:
UserDetails user = _userService.loadUserByUsername(username);
TestingAuthenticationToken token = new TestingAuthenticationToken(user,null);
SecurityContextHolder.getContext().setAuthentication(token);
用户服务是你实现 UserDetailsService 的东西
【讨论】:
【参考方案4】:您可以编写一个扩展 Spring 的 UsernamePasswordAuthenticationFilter
的 custom UsernamePasswordAuthenticationFilter
。
代码如下:
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter;
import org.springframework.security.web.authentication.WebAuthenticationDetails;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
public class CustomUsernamePasswordAuthenticationFilter extends UsernamePasswordAuthenticationFilter
@Override
protected void successfulAuthentication(HttpServletRequest request, HttpServletResponse response, Authentication authResult) throws IOException, ServletException
super.successfulAuthentication(request, response, authResult);
UsernamePasswordAuthenticationToken token = (UsernamePasswordAuthenticationToken) authResult;
WebAuthenticationDetails details = (WebAuthenticationDetails) token.getDetails();
String address = details.getRemoteAddress();
User user = (User) authResult.getPrincipal();
String userName = user.getUsername();
System.out.println("Successful login from remote address: " + address + " by username: "+ userName);
@Override
protected void unsuccessfulAuthentication(HttpServletRequest request, HttpServletResponse response, AuthenticationException failed) throws IOException, ServletException
super.unsuccessfulAuthentication(request, response, failed);
UsernamePasswordAuthenticationToken token = (UsernamePasswordAuthenticationToken) failed.getAuthentication();
WebAuthenticationDetails details = (WebAuthenticationDetails) token.getDetails();
String address = details.getRemoteAddress();
System.out.println("Failed login try from remote address: " + address);
【讨论】:
我不明白这如何解决注册时自动登录的问题。 这是你要找的东西吗:forum.springsource.org/showthread.php?28165-Automatic-login-after-user-registration 我不知道当局会自动使用authenticationManager.authenticate(token)
查找。谢谢。以上是关于如何使用 Spring Security 3.1 以编程方式登录用户的主要内容,如果未能解决你的问题,请参考以下文章
如何在 Spring Security 3.1 中使用 acl_entry 表中的掩码字段?
如何在 Spring Security 3.1 中进行没有身份验证和授权的并发会话控制
使用 Active Directory 的 Spring Security 3.1