gpt4 book ai didi

ruby-on-rails - Sidekiq Ruby on Rails后台作业的幂等设计

转载 作者:行者123 更新时间:2023-12-03 12:59:24 24 4
gpt4 key购买 nike

Sidekiq建议所有作业都是幂等的(可以多次运行而不会出现问题),因为它不能保证一项作业只能运行一次。

在某些情况下,我无法理解实现此目标的最佳方法。例如,假设您有下表:

用户
ID
电子邮件
平衡

运行的后台作业只会使他们的余额增加一些

def perform(user_id, balance_adjustment)
user = User.find(user_id)
user.balance += balance_adjustment
user.save
end

如果此作业运行不止一次,则其余额将不正确。这样的最佳做法是什么?

如果我考虑一下,我可以提出的潜在解决方案是在安排工作之前创建一条记录,例如

待处理的余额调整
用户身份
平衡调整

作业运行时,它将需要为该用户获取一把锁,这样就不会在两个工作人员之间出现竞争状况,然后需要在解除锁定之前更新余额并从待处理的余额调整中删除记录。

那么工作看起来像这样吗?
def perform(user_id, balance_adjustment_id)
user = User.find(user_id)
pba = PendingBalanceAdjustment.where(:balance_adjustment_id => balance_adjustment_id).take
if pba.present?
$redis.lock("#{user_id}/balance_adjustment") do
user.balance += pba.balance_adjustment
user.save
pba.delete
end
end
end

这似乎解决了

a)两名同时工作的 worker 之间的种族状况(尽管您会认为Sidekiq已经可以保证做到这一点?)
b)作业成功运行后被多次运行

这是一个好的解决方案吗?

最佳答案

您走在正确的 rails 上;您要使用数据库事务,而不是redis锁。

关于ruby-on-rails - Sidekiq Ruby on Rails后台作业的幂等设计,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45941980/

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