gpt4 book ai didi

google-app-engine - GAE Go - 如何处理 ErrConcurrentTransaction 数据存储事务错误

转载 作者:IT王子 更新时间:2023-10-29 01:46:15 26 4
gpt4 key购买 nike

我正在编写 Google App Engine Golang 应用程序。在Datastore Transaction documentation , 有注释:

Note: If your app receives an error when submitting a transaction, it does not always mean that the transaction failed. You can receive ErrConcurrentTransaction in cases where transactions have been committed and eventually will be applied successfully. Whenever possible, make your Datastore transactions idempotent so that if you repeat a transaction, the end result will be the same.

这让我相信,如果事务返回 ErrConcurrentTransaction,这意味着数据存储最终将完成事务。然而,阅读RunInTransaction我们可以看到一条注释:

If f returns nil, RunInTransaction attempts to commit the transaction, returning nil if it succeeds. If the commit fails due to a conflicting transaction, RunInTransaction retries f, each time with a new transaction context. It gives up and returns ErrConcurrentTransaction after three failed attempts.

看起来 ErrConcurrentTransaction 是 RunInTransaction 函数的失败状态,这意味着事务永远不会提交。

那么,它是什么?如果 RunInTransaction 返回 ErrConcurrentTransaction,我的代码应该假设什么? Transaction成功了,以后会成功,还是失败了?

最佳答案

具体场景。考虑以下代码段:

err := datastore.RunInTransaction(c, func(c appengine.Context) error {
var err1 error
count, err1 = inc(c, datastore.NewKey(c, "Counter", "singleton", 0, nil))
return err1
}, nil)
// Here, if err is anything other than nil, the datastore-specific
// operations didn't commit to the datastore.

这是我们运行此代码段时的一种可能情况:

  1. RunInTransaction 开始。它calls the provided function .
    • 在该函数中,inc() 操作返回 nil。
  2. RunInTransaction 收到该结果,并尝试完成提交。但由于某种原因,它失败了。 ( Where it can fail. ) 因此 RunInTransaction 从数据存储中接收到一个 ErrConcurrentTransaction。
  3. RunInTransaction tries again .它调用提供的函数。
    • 在该函数中,inc() 操作返回 nil。
  4. RunInTransaction 收到该结果,并尝试完成提交。但由于某种原因,它又失败了。嘿,也许它很忙。
  5. RunInTransaction 耐心地再试一次这个函数。
    • 在该函数中,inc() 操作返回 nil。
  6. RunInTransaction 收到该结果,并尝试完成提交。这一次,底层数据存储允许提交。欢呼!
  7. RunInTransaction 返回 nil 给它的调用者。

所以在这种情况下,您的应用程序会观察到 ErrConcurrentTransactions。你读到的第一个注释是关于整个系统的一般评论:作为一个整体,你的程序可能会遇到 ErrConcurrentTransactions。但这并不意味着您编写的代码将直接触及 ErrConcurrentTransaction。您的代码可能根本看不到此错误。然而 RunInTransaction 正在代表您的代码运行,并且 RunInTransaction 可能会看到该错误。但是事务仍然可以继续进行,因为 RunInTransaction 将重放该函数,直到它成功,或者数据存储非常繁忙以至于它放弃。

如果您从 RunInTransaction 获得 nil 作为最终返回值,则数据存储操作已完成。但如果你得到非零,他们就没有。

请注意,在上面的场景中,RunInTransaction 调用的函数作为重试协议(protocol)的一部分被多次调用。因此,您必须确保传递给 RunInTransaction 的函数没有问题,因为它在数据存储繁忙时尝试使用重试。

关于google-app-engine - GAE Go - 如何处理 ErrConcurrentTransaction 数据存储事务错误,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24706487/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com