ThreadLocal 是否优于 HttpServletRequest.setAttribute("key", "value")?

2023-11-21

Servlet 规范(请参阅我之前的问题)保证同一个线程将执行所有 Filter 和关联的 Servlet。鉴于此,我认为使用传递数据没有任何用处HttpServletRequest.setAttribute如果可以选择使用ThreadLocal(假设你清理得当)。我觉得使用有两个好处ThreadLocal:类型安全和更好的性能,因为没有使用字符串键或映射(除了可能通过(非字符串)线程 ID 进入线程集合)。

有人可以确认我是否正确,以便我可以继续放弃setAttribute?


ThreadLocal 是否优于 HttpServletRequest.setAttribute(“key”, “value”)?

取决于具体的功能需求。

例如,JSF 存储FacesContext in a ThreadLocal。这使您能够访问所有 J​​SF 工件,包括“原始”HttpServletRequest and HttpServletResponse执行的代码中的任何位置FacesServlet,例如托管 Bean。大多数其他基于 Java 的 MVC 框架都遵循相同的示例。

根据你的评论,

我主要需要将 User 和 EntityManager 对象从用户和数据库过滤器传输到 Servlet。我还发现,这些在代码中经常意外地需要,并且我很想在 Servlet 之外使用它们(即在 doGet 调用的嵌套代码中)。我觉得可能有更好的方法来更深入的代码 - 建议?

至于User对于我假设这是一个会话属性的示例,我宁愿遵循与 JSF 相同的方法。创建一个ThreadLocal<Context>哪里的Context是您的自定义包装类保存对当前的引用HttpServletRequest也许还有HttpServletResponse这样您就可以在代码中的任何位置访问它们。如有必要,提供便捷的方法来获取User直接从Context class.

至于EntityManager例如,您可以遵循相同的方法,但我个人不会将其放在same ThreadLocal<Context>,而是另一种。或者,更好的方法是从服务层的 JNDI 获取它,这将允许您对事务进行更细粒度的控制。无论如何,请绝对确保正确处理提交/关闭。从容器接管持久性和事务管理应该非常小心。我真的会重新考虑对使用现有且设计良好的 API/框架(如 EJB/JPA)的厌恶,否则您将面临完全浪费时间重新发明所有已经标准化的 API 和内容的风险。

也可以看看:

  • 从 Web 容器外部的 POJO 检索 Web 会话
  • 基于网络的应用程序设计模式
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

ThreadLocal 是否优于 HttpServletRequest.setAttribute("key", "value")? 的相关文章

随机推荐

  • Java:如何构建基于 Maven 的项目的独立发行版?

    我经常遇到 Java 应用程序或库的发行版 使用 Maven 作为他们的构建工具 遗憾的是 其中一些不提供独立 或可再发行 的 jar 是否可以通过这种方式构建基于 Maven 的应用程序 这构建结果包含所有依赖项并且可以重新分配以开箱即用
  • 如何在 Windows 7 中打开 GCStress?

    我正在调试一个GC堆损坏 来到我想尝试在 WinDbg PageHeap AppVerifier GCStress 下运行程序的步骤 我在文章中发现软件崩溃 错误模块 mscorwks dll 版本 1 1 4322 2379我可以像这样启
  • Node.js NTLM HTTP 身份验证,如何处理 3 种类型

    我正在尝试让 NTLM 身份验证与 Node js 一起工作 我一直在读这个 http davenport sourceforge net ntlm html theNtlmMessageHeaderLayout 我发送标头并获得 Base
  • 为什么 jQuery Extend Deep Copy 不递归复制对象?

    我到处搜索 发现类似的问题 其答案并没有真正解决我的问题 所以如果这看起来像是重复 我深表歉意 但从我的实验看来 jQuery 的深层复制功能实际上并不像所描述的那样工作 或者也许我误读了它的描述 这是一个演示我遇到的问题的示例 http
  • 无法使用自制程序和 php7.4 安装 mcrypt

    操作系统 macOS 11 大苏尔 自制软件 2 5 12 梨版本 12 10 1 我刚刚使用 homebrew 将 mac 上的 php 从 php7 1 升级到 php7 4 brew install 电子邮件受保护 然后 当我尝试安装
  • 如何使用 setuptools 将 Python 标签添加到 bdist_wheel 命令?

    假设我有一个简单的库 它使用设置工具用于包装和分发 在这种情况下 库还需要 Python 3 6 的最低版本 这意味着我的 setup py 将如下所示 from setuptools import setup find packages
  • Modernizr 将笔记本电脑报告为 Chrome 和 FF 中的触摸设备

    有点奇怪 我有一个正在开发的网站 但是 在我的笔记本电脑 华硕 Zenbook 上 某些功能无法使用 我们花了很多时间使用 Firebug 来尝试让它工作 弄清楚它是什么 但没有任何乐趣 然后我注意到这些功能实际上是使用 hover 类在
  • 转义引号和双引号

    我如何正确转义中的引号 param以下命令行中的值 cmd server toto exe batch B param sort1 parmtxt Security ID 1234 Invoke Expression cmd 这当然失败了
  • 在 Laravel 5 中使用 Ajax 并返回 json 数组

    I am new to AJAX and I have been trying to send a request ONSELECT using AJAX and receive a JSON response in laravel 5 这
  • CakePHP:调用其他模型函数

    我如何从模型调用另一个模型中存在的函数 我不想重复代码 我们可以使用模型关系来调用另一个模型中的函数 例如 this gt Model gt ModelOne gt find this gt Model gt ModelOne gt cus
  • Google App Engine - org.datanucleus.exceptions.NucleusUserException:对象管理器已关闭

    为什么下面的代码会导致 org datanucleus exceptions NucleusUserException 对象管理器已关闭 该异常似乎是在 query getResultList 处引发的 public final void
  • 如何转储当前绘图的命令

    在交互模式下 gnuplot 会记住当前绘图的所有设置 当我输入 replot 时它知道要做什么 那么 有没有办法将所有当前设置转储到脚本文件中 See the save命令 您可以按如下方式使用它 save My stuff goes t
  • 等待 css 转换[重复]

    这个问题在这里已经有答案了 我正在使用 css 过渡来设置我的 div 之一的边距 我需要知道如何等待此效果结束 以便我可以调用其他函数 有什么办法吗 我读了一些关于堆栈溢出的其他帖子 但它们看起来都与我的问题不同 Try This所以答案
  • 我应该如何在Delphi中实现一个巨大但简单的索引字符串列表?

    我使用的是 Delphi 2009 我有一个非常简单的数据结构 有 2 个字段 一个字符串 是我需要检索的关键字段 长度通常为 4 到 15 个字符 一个字符串 它是数据字段 可以是任意大小 从 1 个字符到 10 000 个字符 困难在于
  • 批处理文件 - 使用 ping 测试网络连接

    使用批处理文件可以执行以下操作 ping google com 如果返回成功则执行 ECHO 您已连接到互联网 否则返回 ECHO 您没有连接到互联网 您可以使用以下代码片段 echo off Ping www google de n 1
  • 无法检测 TTS(回调)android 的完成。

    我正在开发 Android 应用程序 其中使用文本到语音转换 当我打开应用程序运行文本到语音转换时 我需要什么 完成此操作后 我想做一些事情 我的代码如下所示 public class Mainactivity extends Activi
  • “dict_items”类型的对象不可 JSON 序列化

    如何将 dict item 保存到 json 文件以将其加载到另一个位置 我在浏览器中获取带有 js 的列表并返回到 python 但我无法将其保存为 Json 文件 因为它显示 dict items 类型的对象不可 JSON 序列化 Ja
  • JPA 将默认刷新模式从 AUTO 更改为 COMMIT

    我尝试了多种方法将 FlushMode 更改为完整的应用程序 这是正确的还是有其他方法可以做到这一点 我不想务实地这样做 这是我发现的财产 但它不起作用
  • 我可以在一个查询中执行 mysql 选择、更新和删除吗?

    我可以说优化mysql的众多方法之一就是减少查询次数吗 如果是这样 我可以这样做 Select data gt A from table X Update A from table Y Delete A from table X 在一个查询
  • ThreadLocal 是否优于 HttpServletRequest.setAttribute("key", "value")?

    Servlet 规范 请参阅我之前的问题 保证同一个线程将执行所有 Filter 和关联的 Servlet 鉴于此 我认为使用传递数据没有任何用处HttpServletRequest setAttribute如果可以选择使用ThreadLo