【发布时间】:2015-07-07 13:04:33
【问题描述】:
我被要求实施“访问策略”,以限制直接连接到数据库的应用程序(不是 Web 应用程序)中某个进程的并发执行量。 p>
应用程序在多台机器上运行,如果多个用户尝试调用该进程,则在给定时间只允许执行一次,另一个必须返回错误消息(不等待第一次执行结束)。
虽然我使用的是 Java/Postgres,但这是一个普遍的问题。
鉴于我在多台机器上运行相同的应用程序,我能想到的最简单的解决方案是实现某种“数据库标志”。
类似于检查进程当前是否处于活动状态:
SELECT Active FROM Process
如果它处于活动状态,则返回“并发访问策略错误”。如果没有,请激活它:
UPDATE Process SET Active = 'Y'
执行完成后,只需更新活动标志:
UPDATE Process SET Active = 'N'
但是,我遇到了一个大问题:
- 如果我不使用数据库事务来更改活动标志,并且应用程序被终止,活动标志将永远保留 Y 值。
- 如果我使用数据库事务,第一点就解决了。但是,主机中活动标志的更改(从 N 到 Y)仅在提交后可见,因此其他主机永远不会读取带有 Y 值的活动,因此无论如何都会执行。
有什么想法吗?
【问题讨论】:
-
只是一些初步想法:您可以在单独的事务中设置标志(可能与显式锁定结合使用),或者您可以查看例如hazelcast 用于某种集群范围的锁(尽管这对您的应用程序来说可能有点过分)。
-
与问题没有直接关系,但您可以从使用
INSERT而不是UPDATE中受益。当第一个用户调用该进程时,应在数据库中插入一个新行。当第二个用户调用该进程时,他的INSERT使用相同的主键应该会失败。
标签: java database postgresql concurrency