我有一个关于分布式事务的问题。假设我有 3 个事务程序:
交易A
- 开始
- a=读取(A)
- b=读取(B)
- c=a+b
- 写(C,C)
- 犯罪
交易 B
- 开始
- a=读取(A)
- a=a+1
- 写(一,一)
- 犯罪
交易 C
- 开始
- c=读取(C)
- c=c*2
- 写(A,C)
- 犯罪
所以有5对关键操作:C2-A5、A2-B4、B4-C4、B2-C4、A2-C4。
我应该确保完整性和机密性,您知道如何实现吗?
先感谢您!
我有一个关于分布式事务的问题。假设我有 3 个事务程序:
交易A
交易 B
交易 C
所以有5对关键操作:C2-A5、A2-B4、B4-C4、B2-C4、A2-C4。
我应该确保完整性和机密性,您知道如何实现吗?
先感谢您!
您在帖子中描述的是多用户系统中的常见情况。不同的会话同时使用相同的表和相同的行启动事务。这里有两个问题:
(您的场景仅说明了这些问题中的第一个)。
第一个问题的答案是隔离级别。这是跨会话未提交事务的可见性的定义。ANSI 标准规定了四个级别:
不同的风格或数据库以不同的方式实现这些,并不是所有的数据库都支持它们。例如,Oracle 只支持 READ COMMITTED 和 SERIALIZABLE,它把 SERIALIZABLE 实现为一个 snapsot(即它是一个只读事务)。但是,它使用多版本并发控制来防止 READ COMMITTED 事务中的不可重复读取。
所以,回到你的问题,答案是:设置适当的隔离级别。合适的级别取决于您的数据库支持的级别以及您希望发生的行为。可能您想要 READ COMMITTED 或 SERIALIZABLE,即您希望您的事务在数据值与事务开始一致的基础上继续进行。
至于另一件事,答案更简单:事务必须在开始更新表之前对表或最好只对所需的行进行锁定。这确保事务可以继续更改这些值而不会导致死锁。这称为悲观锁定。这在使用连接池的应用程序(即大多数基于 Web 的应用程序)中是不可能的,而且情况要复杂得多。