gpt4 book ai didi

ajax - 手动身份验证时,使用 sessionRegistry 登录用户不起作用

转载 作者:行者123 更新时间:2023-12-03 18:39:05 24 4
gpt4 key购买 nike

我使用 spring security3 和 spring mvc3 来构建一个 web 项目。有一个叫index.jsp的页面,会显示登录用户名和在线用户数
此屏幕的顶部。登录系统有两种方式:

  • 从登录页面,使用'j_spring_security_check'的默认配置帖子
  • ajax 登录手动认证

  • 当我使用登录页面登录到索引页面时,在线信息计数和用户名都显示正确。
    但是当我使用ajax登录(手动认证)时,出现问题:在线用户数没有更新,它总是显示0而用户名可以正常显示。
    Controller 的一部分:
    @Autowired
    @Qualifier("authenticationManager")
    AuthenticationManager authenticationManager;
    @Autowired
    SecurityContextRepository repository;

    @RequestMapping(value="/ajaxLogin")
    @ResponseBody
    public String performLogin(
    @RequestParam("j_username") String username,
    @RequestParam("j_password") String password,
    HttpServletRequest request, HttpServletResponse response) {
    UsernamePasswordAuthenticationToken token = new UsernamePasswordAuthenticationToken(username, password);
    try {
    Authentication auth = authenticationManager.authenticate(token);
    SecurityContextHolder.getContext().setAuthentication(auth);
    repository.saveContext(SecurityContextHolder.getContext(), request, response);
    logger.info("Authentication successfully! ");
    return "{\"status\": true}";
    } catch (BadCredentialsException ex) {
    return "{\"status\": false, \"error\": \"Bad Credentials\"}";
    }
    }

    spring-security.xml
    <beans:beans xmlns="http://www.springframework.org/schema/security"
    xmlns:beans="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://www.springframework.org/schema/beans
    http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
    http://www.springframework.org/schema/security
    http://www.springframework.org/schema/security/spring-security-3.0.3.xsd">

    <http auto-config="true" use-expressions="true">
    <intercept-url pattern="/login" access="permitAll" />
    <intercept-url pattern="/index" access="permitAll" />
    <form-login login-page="/login" default-target-url="/index"
    authentication-failure-url="/loginfailed" />
    <logout logout-success-url="/logout" />

    <session-management invalid-session-url="/index">
    <concurrency-control max-sessions="1"
    error-if-maximum-exceeded="false" />
    </session-management>
    </http>

    <authentication-manager alias="authenticationManager">
    <authentication-provider>
    <jdbc-user-service data-source-ref="dataSource"

    users-by-username-query="
    select login_id,login_pwd, is_enabled
    from t_user where login_id=?"

    authorities-by-username-query="
    select u.login_id, r.authority from t_user u, t_roles r
    where u.u_id = r.u_id and u.login_id =? " />
    </authentication-provider>
    </authentication-manager>

    我用来获取在线登录用户数的方法:
    public class BaseController {
    protected Logger logger = Logger.getLogger(this.getClass());

    @Autowired
    SessionRegistry sessionRegistry;

    @ModelAttribute("numUsers")
    public int getNumberOfUsers() {
    logger.info("in getNumberOfUsers() ...");
    return sessionRegistry.getAllPrincipals().size();
    }
    }

    用于显示登录用户名的代码:
    <div>
    <security:authorize ifAllGranted="ROLE_USER">
    <p><a href="#TODO">Welcome <security:authentication property="principal.username" />!</a> &nbsp;&nbsp;&nbsp;
    <a href="<c:url value="/j_spring_security_logout" />">Logout</a></p>
    </security:authorize>
    </div>

    用于显示登录用户数的代码:
    <div style="color:#3CC457">
    ${numUsers} user(s) are logged in!
    </div>

    我猜这是因为当我手动验证时,spring security 不会为用户创建新 session 。 我通过编写自定义的 SessionCounterListener 来验证它。
    public class SessionCounterListener implements HttpSessionListener {
    private Logger logger = Logger.getLogger(this.getClass());
    private static int totalActiveSessions;

    public static int getTotalActiveSession(){
    return totalActiveSessions;
    }

    @Override
    public void sessionCreated(HttpSessionEvent event) {
    totalActiveSessions++;
    logger.info("sessionCreated - add one session into counter" + event.getSession().getId());
    }

    @Override
    public void sessionDestroyed(HttpSessionEvent event) {
    totalActiveSessions--;
    logger.info("sessionDestroyed - deduct one session from counter" + event.getSession().getId());
    }

    }

    以下是操作序列日志文件的关键内容:正常登录-> 正常注销-> ajax 登录-> ajax 注销。
    sessionDestroyed - deduct one session 1spueddcmdao019udc43k3uumw
    sessionCreated - add one session 14nro6bzyjy0x1jtvnqjx31v1
    sessionDestroyed - deduct one session 14nro6bzyjy0x1jtvnqjx31v1
    sessionCreated - add one session e6jqz5qy6412118iph66xvaa1

    实际上,ajax login/logout 没有给出任何输出。

    那么现在,我怎样才能获得正确的登录用户数?为什么不同的认证方式有不同的处理 session 的方法?任何帮助将不胜感激。

    最佳答案

    当您手动添加 PrincipalSecurityContext ,它不会将用户添加到 SessionRegistry .您需要将用户 session 添加到 SessionRegistry手动。

    SecurityContextHolder.getContext().setAuthentication(auth);
    sessionRegistry.registerNewSession(request.getSession().getId(), auth.getPrincipal());

    希望能帮助到你!!

    关于ajax - 手动身份验证时,使用 sessionRegistry 登录用户不起作用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18271727/

    24 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com