2009-09-22 60 views
3

我有一个多线程,多服务器Web应用程序,具有休眠和弹簧管理AOP事务。问题是,我需要维护内存中的数据,并保持与数据库的状态保持最新......实质上,我正在实现内存缓存。如何让我的pojos交易?

现在,有什么办法让我的内存中pojos事务与hibernate/spring事务相同吗?我有服务调用分层深入30个类,我永远不知道提交将发生在哪里。我有什么选择?

回答

2

如果我理解得很清楚您的需要,您在某些情况下会问些微妙的东西。让我尝试一个例如,要检查如果我理解正确

  1. 线程T1读取POJO p在缓存中,得到版P1。
  2. 线程T2读取缓存中的pojo P,获取版本P1。
  3. 线程T2启动事务,读取相同的pojo,修改一个创建版本P2的值。
  4. 线程T1读取缓存中的pojo P,仍然获得版本P1。这要求对于点3,T2收到版本P1的副本P2,而不是同一个对象。
  5. 线程T2保存P,T1或T2没有任何变化,它们有不同的版本。
  6. 线程T2关闭交易:
    a。如果回滚,则T2将使用P1,如T1所示。 b。如果提交,T2将继续使用P2。但是现在T1也必须使用P2。

您可以看到这是一个复杂的问题,请不要低估它。 在理论层面上有许多问题需要解决(当你编码时你会有更多的问题)。 如果您想成功使用它,您的架构将需要非常清晰。 如果不是,你冒着心理上的理智;-)

首先,你需要确保你真的想要这样的东西!


如果你真的想要的..

我建议使用技术规范(AOP,ThreadLocal的),以隐藏你的功能代码这个棘手的复杂性。

  • 很可能您的提交/回滚已经通过AOP完成,所以这应该不成问题。

  • 要隐藏P实例的检索(有时是存储高速缓存中的实例,有时是副本):使用名为Store的类将值存储在高速缓存中,并具有类型为Store的ThreadLocal变量。我会用一个ThreadLocal变量为你的当前线程:

    • 的存储实例只能在你的交易AOP代码进行更改,而不是在你的功能代码
    • 你的功能代码使用当前的ThreadLocal实例用于操纵实体(保存等)
    • 以外的事务,ThreadLocal实例是缓存的,我们称之为CACHE。
    • 输入交易为当前线程设置不同的ThreadLocal实例;该类是Store的一个子类,它会在您请求时返回缓存对象的副本;如果保存了某些类,那么该类还将记忆(因此您需要使用此特殊API保存它们,或者在您的常规保存API中通知)
    • 回滚事务将抛弃ThreadLocal实例,重新安装CACHED之一当前线程
    • commiting交易将采取一切记忆的数据库操作的ThreadLocal实例,应用修改缓存的实例,并重新安装缓存实例当前线程的
1

不使用Hibernate的2nd level cache不能满足您的要求? JBoss Cache提供程序既是分布式的,也是事务性的。

如果这不适合你,你将不得不解释为什么你真的试图获得有意义的回应。