2

我目前必须使特定的 Java servlet 实现线程安全。代码不是我写的,我也没有参与它的设计或任何事情。我“只是”必须使它成为线程安全的:)

我不是线程安全的初学者,但也不是专业人士。Servlet 对我来说(或多或少)是全新的。我已经完成了一些教程并了解了有关 servlet 的基础知识,但仅此而已。我能找到的所有关于使 servlet 线程安全的教程都相当肤浅,而且我还有一些未解决的问题,我似乎无法找到答案。一些帮助将不胜感激。

1.)据我了解,HttpServletRequests 和 HttpServletResponses 不在不同的线程之间共享,所以我不需要同步它们的读写访问(这是正确的吗?)。但是 HttpServletRequestWrappers 等呢?

2.) 我必须同步对 getServletContext() 返回的 ServletContext 对象的访问,尤其是在我使用 setAttribute() 时,对吧?

3.) HttpServletRequests 有一个 getCookies() 方法。这些 Cookie 是否可能在不同的请求之间共享,或者每个请求都有自己的 Cookie 对象(即使它们代表相同的“真实”cookie)?换种方式问:我是否必须同步对返回的 cookie 对象的访问?

感谢您花时间阅读我的问题。我期待着你的回答:)

4

3 回答 3

1
  1. Your understanding is correct. Actually thread is created for each request. So HttpServletRequest and HttpServletResponse are local to thread. So no sharing of these two. You do not need to synchronize them. HttpServletRequestWrapper and HttpServletResponseWrapper are the classes which provide a convenient implementation of the HttpServletRequest and HttpServletResponse interfaces respectively. You do not need to worry about them in synchronization context.

  2. Definitely you have to provide synchronization for ServletContext object returned by getServletContext() because it is shared between servlets in your application.

  3. As HttpServletRequest is local to thread created by container to serve the request. So cookies are also local to that thread and those are not shared. So no need to provide synchronization to cookies.

Few concepts :

  1. Servlets are always singlton in your application. i.e. only one object is created.
  2. For each request a different thread is created(actually obtained from Thread Pool). Following things are local to thread : HttpServletRequest, HttpServletResponse
于 2012-08-24T09:26:02.507 回答
1

Servlet 不是线程安全的,因为应用程序服务器可以维护 Servlet 的单个实例或实例池,并在多个传入请求之间共享它们。因此,servlet 不应该有任何状态(即 servlet 对象级变量不是线程安全的)。Servlet 规范以前有SingleThreadModel接口来强制给定的 servlet 是线程安全的,但我猜自 2.3 以来已被弃用。

回应:

  1. 对,这些是 doGet 和 doPost 等 HTTP 方法的参数,因此无需同步对这些方法的访问。

  2. 正确,因为 getServletContext() 返回一个上下文级对象,所有 servlet 和运行给定 servlet 的所有线程都可以访问该对象。

  3. 每个请求都带有自己的一组 cookie。同样,这是从方法参数 HttpServletRequest 获得的,因此访问不需要同步。

于 2012-08-24T09:09:44.463 回答
1

当您使 servlet 线程安全时,您很少需要同步。Servlet 从一开始也应该是线程安全的,因为单个 Servlet 实例可能被多个用户使用。此外,您不能相信只有一个 servlet 实例,除非您的 servlet 容器指定始终只有一个。

1)处理请求和响应对象时不需要同步,因为一次只有一个线程可以处理一个请求。

2) 您应该尝试以一种无需在 servlet 内的 ServletContext 中设置任何值的方式来设计您的应用程序。通常 ServletContext 在启动时被初始化,然后被 servlet 或过滤器用作只读。我不确定它是否应该是线程安全的,但是如果你在同一个请求中设置多个值,那么无论如何你都必须同步,这样读取这些值的 servlet 就不会被弄乱。但这是基本的线程安全问题,与 servlet 无关。

3) cookie 不需要同步,因为它们处理当前请求并且只有一个线程可以完成。

新的 servlet 容器允许异步模型,其中多个线程可能处理单个请求,但一次仍然是一个线程。

于 2012-08-24T09:23:13.830 回答