gpt4 book ai didi

java - Java Servlet 中静态变量的使用(例如在 AppEngine 中)

转载 作者:行者123 更新时间:2023-12-01 06:33:59 25 4
gpt4 key购买 nike

我有一个应用程序,其中 Servlet 有一个名为 Update(ReqIn, ReqOut) 的方法。我从 doGetdoPost 调用它并传递 Request 和 Response 变量,然后由 Update(...) 来填充输出以下静态变量:

...
public class Server extends HttpServlet {

public static HttpServletRequest In = null;
public static HttpServletResponse Out = null;

public static boolean isDebug = true;
public static boolean isPost = false;

public static String URL = "";
public static String IP = "0.0.0.0";
public static Cookie[] Cookies = null;

public static UserClass User = null;
public static boolean isLoggedIn = false;


...
}

基本上抽象最常用的东西并根据每个请求更新它。这还允许我从网站中的任何位置访问 IP 地址和当前用户数据,只需编写 Server.User.getUsername(); 即可,而不是每次加载页面时创建一个新的类实例并使用更长的访问代码:Server.getUser().getUsername();

现在的问题是:在多用户环境(AppEngine 上的 Jetty)中,这会带来任何问题吗?例如。一些线程/竞赛问题导致用户看到不正确的 IP 地址,或者在极端情况下突然以不同用户身份登录?

或者我应该重写代码并将其更改为 Public UserClass User 而不是 Public static UserClass User 等?

最佳答案

使用静态是一个非常糟糕的主意,因为如果您同时收到两个请求,那么它们将互相覆盖。通过这个简单的例子来看看会出现什么问题:

1:public class Server extends HttpServlet {
2: public static int requestNo = 0;
3: public void doGet(HttpServletRequest req, HttpServletResponse resp)
4: {
5: requestNo++;
6: resp.getWriter().println(requestNo);
7: }
8:}

现在想象一下以下时间线:

请求 1 进入并处理直至第 5 行(包括第 5 行)。
请求 2 进来并完成处理。
请求 1 继续处理。

两个请求都将获得文本“2”,而不是一个获得“1”,一个获得“2”。这是国家被践踏的一个简单例子。

现在,回答您问题的第二部分;

Or should I rewrite code and change it to Public UserClass User instead of Public static UserClass User, etc?

不,这还不够好,因为 J2EE 规范允许 servlet 容器使用类的一个实例来服务该 servlet 映射的所有请求,也就是说,实例级变量将具有完全相同的值作为静态效果,它们在所有请求之间共享。

这只剩下三个实际选项:

  1. 将所有内容放入 HTTPSession 中。这里的问题是,这是一个 map ,因此您失去了类型安全性,并且很难看到正在使用的东西。
  2. 创建一个 Holder 类来保存所有状态并将其传递到各处。这好一点,因为至少你不会失去类型安全,但你仍然没有完全的可见性。
  3. 传递各个所需的元素。

关于java - Java Servlet 中静态变量的使用(例如在 AppEngine 中),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/1849491/

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