带有 2 个不同请求的 HttpSession 问题 [英] troubles with HttpSession with 2 different requests

查看:53
本文介绍了带有 2 个不同请求的 HttpSession 问题的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在开发基于 Java 的后端,但在管理用户会话时遇到了问题.

I'm developing a Java based backend and I'm having troubles while managing my user sessions.

我想在会话中为每个用户存储一些个人信息,因此我实现了一个用于登录目的的 Servlet,如果登录成功,它会创建一个会话:

I would like to store some personal information for each user in the session, hence I implemented a Servlet for login purpose which creates a session if the login is successful:

    @WebServlet("/LoginUserWithPassword")
@MultipartConfig(fileSizeThreshold = 1024 * 1024 * 2, // 2MB
maxFileSize = 1024 * 1024 * 10, // 10MB
maxRequestSize = 1024 * 1024 * 50) // 50MB
public class LoginUserWithPassword extends HttpServlet {
    private static final long serialVersionUID = 1L;
    static Logger log = Logger.getLogger(LoginUserWithPassword.class);


    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {

        request.setCharacterEncoding("UTF-8");
        response.setCharacterEncoding("UTF-8");


....
        HttpSession session = request.getSession();
        session.getServletContext().getContext("/{applicationContextRoot}").setAttribute("nom",usr.nom);
        session.getServletContext().getContext("/{applicationContextRoot}").setAttribute("prenom", usr.prenom);
        session.getServletContext().getContext("/{applicationContextRoot}").setAttribute("login", usr.email);
        session.getServletContext().getContext("/{applicationContextRoot}").setAttribute("id", String.valueOf(usr.id_user));
        session.getServletContext().getContext("/{applicationContextRoot}").setAttribute("id_right",String.valueOf(ur.id_right));
        session.getServletContext().getContext("/{applicationContextRoot}").setAttribute("right",url.right);
        session.getServletContext().getContext("/{applicationContextRoot}").setAttribute("session",session.getId());

然后,在客户端(JSP/Javascript),我正在检索会话信息.

then, on the client side (JSP/Javascript), I'm retrieving the session information.

考虑一个 user1,他使用以下 Javascript 代码在浏览器 (Chrome) 上成功登录:

Considering a user1, who is logging successfully on a browser (Chrome) with the following Javascript code:

Glogin = '<%= (String) (request.getSession().getServletContext().getContext("/{applicationContextRoot}").getAttribute("login")) %>';
        Gsession = '<%= (String) (request.getSession().getServletContext().getContext("/{applicationContextRoot}").getAttribute("session")) %>';

        console.log("login from session: "+Glogin);
        console.log("Session ID: "+Gsession);

我可以看到以下控制台日志:

I can see the following console logs:

login from session: admin3@toto.com
Session ID: 7D6638EA7167580F4C1BD4D51FAD3C9C

然后我使用另一个浏览器 (FF) 在同一台计算机上对 user2 进行第二次登录,控制台日志中有以下内容:

Then I'm performing a second login of user2 on the same computer with another browser (FF), I have the following in the console logs:

login from session: admin@toto.com
Session ID: 376C57F6ACB08CD3B66AB8406DB72984

在那个阶段一切都很完美,我可以在每个会话中检索我各自的属性,但是如果我刷新 user1 的浏览器,我会检索用户 2 的会话 ID....并丢失我的 user1 会话上下文.

at that stage everything is perfect, I can retrieve my respective attributes on each session,but If I refresh the browser of user1, I retrieve the session ID of user 2....and lose my user1 session context.

你知道我为什么会有这种行为吗?可能是我实现会话管理的方式不正确?

Do you have an idea why I'm getting such behavior ? may be my way of implementing session management is not correct ?

推荐答案

不要把它放在 ServletContext 中,它会覆盖之前的值.而是将它放在当前会话中,如下所示:

Dont put it in ServletContext, it will override the previous values. Instead put it in the current session like given below:

request.getSession().setAttribute("nom",usr.nom);

并从像这样的会话中检索 JSP 上的这些值

And retrieve these values on JSP from session like

(String)session.getAttribute("nom");

目前您正在遵循类似

Browser(CLient) ---> War 1 上调用 JSP -----> war 2 上调用 Servlet

Browser(CLient) ---> Calling JSP on War 1 -----> Calling Servlet on war 2

您可以在浏览器(客户端)之间保持会话 ----> 在 war 1 上调用 JSP

You can maintain session between Browser(Client) ----> Calling JSP on war 1

当你验证你的用户时,用户的详细信息来自war 2,用户的详细信息可以被捕获为管道符号分隔在一个字符串中,字符串可以保存在ServletContext中(注意仅在war 2中执行此代码)

When you authenticate your user the details of Users from war 2, the details of users can be captured in as pipe symbol separated in a string that String can be saved in ServletContext (Note perform this code in war 2 only)

    Map<String. String> allUsers = new HashMap<>();
// add key as user id and value is comma separated in string
    ServletContext servletContext =request.getSession().getServletContext().getContext("contextPath")
    servletContext.setAttribute("users",allUsers );

您的 servlet 应该将用户 ID 返回给 JSP 以作为响应

Your servlet should return user id to JSP in response

war 2 ----> 将 user id 返回给 war 1 中的 JSP

war 2 ----> returning user id to JSP in war 1

现在您应该将此用户 ID 保存在您在浏览器(客户端)-----> 战争 1 上的 JSP 之间维护的会话中.

Now you should save this user id in the session that you are maintaining between Browser (CLient) -----> JSP on war 1.

每当您想在 servlet 上下文中使用存储在 war 2 中的值时,您可以在 war 1 中的 JSP 中使用以下代码

Whenever you want to use values that you had stored in war 2 in servlet context, you can use below code in JSP in war 1

ServletContext servletContext =request.getSession().getServletContext().getContext("contextPath")
servletContext.getAttribute("user"); 

注意:您不能在两个 war 文件之间共享会话,但可以在它们之间共享对象.

Note : You can not share session between two war files however you can share objects between them.

愿这对你有帮助.

这篇关于带有 2 个不同请求的 HttpSession 问题的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆