【问题标题】:Prioritizing Transactions in Google AppEngine在 Google AppEngine 中优先处理事务
【发布时间】:2014-09-19 21:59:24
【问题描述】:

假设我需要对可能同时发生的数据存储实体执行两种不同类型的写入操作,例如:

  • 对条目持有写锁的客户端会更新条目的内容
  • 客户端请求刷新写锁(更新锁的过期时间戳)

由于只有在客户端持有当前写锁的情况下才允许内容更新操作,我需要在事务中执行锁检查和内容写入(除非我缺少另一种方式?) .此外,由于客户端需要首先被确认为当前的锁持有者,因此必须在事务中进行锁刷新。

锁刷新是一个非常快速的操作。

内容更新操作可能相当复杂。把它想象成客户端向服务器发送一个复杂的更新脚本,服务器在内容上执行。

鉴于此,如果这两个事务之间存在冲突(如果它们同时执行),我宁愿锁刷新操作失败而不是复杂的内容更新。

有没有一种方法可以“确定”内容更新事务的优先级?我在文档中看不到任何内容,我想这不是一个特定的功能,但也许我可以使用一些技巧?

例如,如果我的内容更新读取条目,将其写回并稍作修改(不提交事务),然后执行冗长的操作并最终写入结果并提交事务,会发生什么?是否会立即应用第一次写入并导致同时锁定刷新事务失败?还是所有写入都保留到最后提交事务?

有没有保持两个交易开放的事情?还是在事务中进行中间提交?

显然,我可以将我的内容更新拆分为两个事务:第一个设置“请不要乱来!”标志,第二个(稍后)写入更改并清除该标志。

但也许还有其他一些技巧可以通过更少的读取/写入/事务来实现这一点?

我的另一个想法是有 3 个不同的数据“块”:当前锁持有者 (LH)、锁到期 (EX) 和正在修改的内容 (CO)。 lock-refresh 操作需要在一个事务中读 LH 和写 EX,而 content-update 操作需要在一个事务中读 LH、读 CO 和写 CO。有没有办法将数据分成三个实体,并以某种方式让事务只跨越所需的实体?由于这两个操作永远不会修改 LH,这可能有助于避免冲突吗?

【问题讨论】:

    标签: google-app-engine transactions


    【解决方案1】:

    数据存储使用乐观并发控制,这意味着(数据存储原语)事务会一直等待,直到它被提交,然后只有在其他人没有先提交时才会成功。通常,应用程序会使用新数据重试失败的事务。无法修改这种先赢行为。

    了解数据存储事务是强一致的可能会有所帮助,因此客户端可以首先使用同步数据存储调用提交锁刷新,当该调用返回时,客户端可以确定它是否获得或刷新了锁。然后客户端可以继续其更新和锁定清除。您描述的锁刷新和更新可能从同一个客户端同时发生的情况听起来是可以避免的。

    我假设您需要锁定机制来防止来自其他客户端的写入,同时锁定所有者执行多个数据存储原语事务。如果客户端在释放锁之前实际上只进行了一次更新,并且它可以在几秒钟内完成(远在数据存储 RPC 超时之前),那么您可能只需要一个具有乐观并发控制和重试的原始数据存储事务即可。但是对于简单的序列化(例如,对用户界面中的记录的编辑)来说,锁定可能是一个好主意,其中用户点击 UI 中的“编辑”按钮,您希望这样可以保证用户有一些时间准备并在不被其他人更改记录的情况下提交更改。 (这是否是您想要的用户体验是您的决定。:))

    【讨论】:

      猜你喜欢
      • 2011-03-22
      • 1970-01-01
      • 2023-03-24
      • 1970-01-01
      • 2018-06-10
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-04-11
      相关资源
      最近更新 更多