2

在我的 XPages Web 应用程序(Xpages 是一种基于 JSF 的 Lotus Notes 技术)中,我需要一个动态映射来存储会话 ID 和上次访问时间(以毫秒为单位)。这是作为TreeMap应用程序范围内的 bean 实现的。对应用程序的每次初始访问都会将当前会话注册到此 bean 中的 TreeMap。此映射只允许有限数量的会话条目,并且不注册多余的会话。地图也会不时从旧会话条目中清除,以便可以注册新会话。我需要知道这是否是应用程序 bean 的可接受方法/使用。我知道我可以将会话条目临时存储在外部数据库(非莲花笔记)中,但我工作的公司不允许我这样做。这种方法会导致我遇到潜在的问题吗?如果是,我还有其他方法可以做到这一点吗?

4

2 回答 2

5

这听起来像是对应用程序 bean 的完全有效的使用,但我要提供两个建议。第一种是使用 ConcurrentSkipListMap 而不是 TreeMap。前者是线程安全的,而后者不是。在与较低范围交互时,线程安全通常并不重要,因为每个用户只能写入自己的会话、视图和请求范围,但所有用户都可以写入应用程序范围,因此可以想象并发写入可能会发生,特别是在用户负载较重的应用程序中。第二个建议是提醒注意每个会话有多少信息存储在应用程序 bean 中。由于所有用户都可以访问 bean,因此理论上可能会无意中向其他用户公开太多有关用户的信息。如果你' 除了上次访问时间之外,只存储会话名称或 ID,你会没事的。但是,如果您实际上存储了一个指向每个用户会话范围的指针,您可能会意外地为用户缓存的数据提供一个窗口,而其他用户不应访问这些数据。我从来没有真正看到有人被这个咬过,但是在应用程序范围内存储任何用户特定的信息时,记住这一点总是很重要的。

于 2012-07-29T19:46:48.013 回答
1

确实,这是对 Application Scope 的一个很好的使用。尽管如此,该TreeMap集合并不是适合您的情况的最佳方法,这存在一些问题:

  • 当 2 个请求想要修改容器中的数据时的并发问题。
  • 如果您的应用程序必须水平扩展,则TreeMap每个托管 bean 将有 2 秒。

一个好的方法是使用缓存系统。有很好的缓存库可以满足这些要求,我已经测试了ehcache ,它提供了处理数据和库的并发管理,以防您有 2 个或更多节点来部署应用程序,您还可以配置算法来清除缓存基于 LRU(不常用)或 FIFO(先进先出)。

使用外部数据库处理会话 ID 可能会花费一些时间来获取/设置数据(它可能非常少,但仍然是磁盘 I/O 操作)。对于这个问题,您可以将BigMemory用作驻留在 RAM 中的外部数据库,或者像BigTable这样的 NoSQL 数据库这样的 NoSQL 数据库。

注意:我不为 ehcache 工作,也没有以商业方式关联,我已经对其进行了测试,它满足了我的需求。还有其他缓存系统库,如JBoss Cache其他您可以评估和使用的缓存系统库。

于 2012-07-29T20:10:59.167 回答