【问题标题】:SecurityContextHolder.getContext().getAuthentication() returning nullSecurityContextHolder.getContext().getAuthentication() 返回 null
【发布时间】:2014-04-07 03:14:36
【问题描述】:

我想使用以下代码从 spring Security 中手动绕过用户:

User localeUser = new User();
UsernamePasswordAuthenticationToken auth = new UsernamePasswordAuthenticationToken(localeUser ,null, localeUser .getAuthorities());
SecurityContext securityContext = SecurityContextHolder.getContext();
        securityContext.setAuthentication(auth);
        // Create a new session and add the security context.
        HttpSession session = request.getSession(true);
        session.setAttribute("SPRING_SECURITY_CONTEXT", securityContext);
return "dummyLogin";

虚拟登录页面(由图块处理)在内部调用同一控制器中的不同请求映射,我试图在其中获得类似这样的身份验证。

SecurityContextHolder.getContext().getAuthentication()

我在哪里得到空值?

【问题讨论】:

  • 您将一个空的 User 对象传递给 UsernamePasswordAuthenticationToken 构造函数。可能这就是你得到 null 的原因。
  • 也是一个空密码(我认为这也是非法的)。也许如果你显示堆栈跟踪?
  • password 可以为空,我宁愿在创建会话后检查会话是否相同,并且在运行 getAuthentication 的代码中。记录你的 session.getId() 来检查它。
  • 您是否只想为某些特定页面或特定用户或全部绕过安全性?
  • 我想绕过该特定会话 ID(用户)的所有页面

标签: java spring security spring-security


【解决方案1】:

所以,我发现了真正的问题! 问题是我在 security-context.xml 中用 security="none" 标记了整个控制器。 所以,当它从第一个链接反弹到第二个链接时,它没有传递任何安全上下文!! 抱歉,麻烦各位了。

【讨论】:

  • 帮助我解决了我的问题,我将某些 url 模式放在忽略配置中,结果是这些控制器中的安全上下文为空,从忽略配置中删除使该控制器变得安全,最终获得安全上下文为想要的
【解决方案2】:

附加答案:如果您想获取非安全 url 的登录用户详细信息,则可以将它们添加到安全 url 并分配为“permitAll”,如下所示:

<http>
    //...

    <intercept-url pattern="/your/url/**" access="permitAll"/>

    //...
</http>

然后,您将能够检查登录用户是否已登录或获取凭据。

【讨论】:

    【解决方案3】:

    您的 localUser 为 null。因此身份验证变为 null。因此未将身份验证对象添加到安全上下文中。

    请看文档

    http://docs.spring.io/spring-security/site/docs/3.0.x/apidocs/org/springframework/security/core/userdetails/User.html

    最好有一个customUserDetailsS​​ervice

    public class CustomUserDetailsService implements UserDetailsService 
    
    //implement the method which return a UserDetails Object
    public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException 
    

    那么你可以使用

        UserDetails userDetails= customUserDetailsService.loadUserByUsername("name"); 
    Authentication authentication= new UsernamePasswordAuthenticationToken(userDetails, null, userDetails.getAuthorities()) ; 
    SecurityContextHolder.getContext().setAuthentication(authentication);
    

    【讨论】:

    • localUser 不为空!它是应用程序的自定义用户对象,在初始化时自行在其中创建了 ID 和详细信息。
    【解决方案4】:

    试试这个:

    Authentication authentication=SecurityContextHolder.getContext().getAuthentication();
    localeUser .setUserNm(authentication.getName());
    

    【讨论】:

    • 你不必评论它。相反,您可以添加您的 commnet 来回答
    猜你喜欢
    • 2013-07-08
    • 2015-08-17
    • 2019-04-28
    • 2019-06-29
    • 2017-04-25
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多