[英]In a Rails app running on multiple servers, how can I make sure a rake task runs only once?
我有一個 Rails 應用程序在生產中的 2 個服務器上運行。
我有一個 rake 任務,它運行一些導入,然后向用戶發送電子郵件。 我現在收到 2 封電子郵件,因為有 2 台服務器。
為了避免這種情況,我嘗試創建一個表my_import_run
。
上述算法的實現如下所示:
def self.import(search_date = Date.current)
if 0 == MyImportRun.count || !MyImportRun.where(:last_run => Date.today).any?
# the code to run import job and send email goes here
#
#
#
#
MyImportRun.delete_all
MyImportRun.new(:last_run => Date.today)
MyImportRun.save
end
但即使在執行上述代碼后,我仍然收到 2 封電子郵件 - 我不知道為什么。 我想知道兩個導入可能在完全相同的時間運行,因此它們都不會找到具有當前日期的記錄並運行導入,發送電子郵件並刪除所有記錄並添加具有當前日期的記錄。
有沒有一種干凈的方法來避免這種情況發生? 據我所知,rake 任務會自動導入到 Linux 中的 cron 作業中; 所以我不能只從一台服務器上刪除 rake 文件。
我確信必須有一種干凈的方法來避免這種重復。
如果您使用Whenever
和Capistrano
該功能也可以用roles
:在部署文件,您可以設置角色的列表:
server 'first-server', user: 'deployer', roles: %w{app db web sidekiq job}, primary: true
server 'second-server', user: 'deployer', roles: %w{app db web sidekiq job2}
在schedule.rb
:
every 1.day, at: '5:00am', roles: [:job] do # this task will be run only on the first server
rake "-s sitemap:refresh:no_ping"
end
every 1.day, at: '5:00am', roles: [:job2] do # this only on second
rake "another_rake_task"
end
更多細節你可以找到這個
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.