复制表上的async_dirty

时间:2015-09-22 04:45:05

标签: transactions erlang mnesia

假设我有一个Mnesia表T,它在两个节点A和B上复制{T, Key, Value},dirty_write定义为:

dirty_write(T, Tuple) ->
    Fun = fun() ->
                  mnesia:write(T, Tuple, write)
          end,
    mnesia:activity(async_dirty, Fun, [], SomeMod).

R1 = {T, 1, 2}R2 = {T, 1, 3}是两条记录,如果我执行(可能同时发生):

dirty_write(T, R1) %% on node A
dirty_write(T, R2) %% on node B

这会在T上引入某种不一致/错误吗?

1 个答案:

答案 0 :(得分:0)

我发现您的记录R1 = {1, 2}R2 = {1, 3}有点不合常规,因为mnesia惯例会使R1 = {T, 1, 2}R2 = {T, 1, 3}更常见,但实际上并不一定是适当实现你的回调模块。但是,你的代码可能不像其他Erlang开发人员所期望的那样。

对于您提供的示例,当然不清楚密钥是什么,但最合理的猜测可能是您的“记录”的第一个元素,在这种情况下为1。这意味着你要在2个节点上更新相同的记录。

在这种情况下,我认为没有理由因为这两笔交易本身而存在任何不一致的风险;没有风险你的桌子会包含任何实际上无效的东西,但当然一个人会覆盖另一个,而且没有一个作家知道哪个会赢。可能如果你觉得你想以这种方式做一个异步的脏写,那么我希望你已经决定哪一个赢了并不重要......

然而......读取或以其他方式使用您正在更新的记录的其他事务/操作可能会访问所写记录值的EITHER,或者在这些写入之前使用该值,然后执行他们所做的任何事情所以...那么问题是(并且它完全依赖于用例)任何其他操作(交易或非交易)都会受到这种不确定性的不利影响。这里的主要风险是,例如,某些其他记录可能是根据正在编写的记录{T, 1, 2}编写的,但是在完成所有操作的时候,它实际上以{T, 2, 3}为准。 ..这可能适用于您的应用程序,也可能不适用,它可能会也可能不会成为问题!

有一个原因,mnesia提供不同级别的安全性与性能(异步脏,同步脏和完全同步事务),这是因为只有最终开发人员/集成人才有足够的知识来决定需要什么样的安全性和性能。

相关问题