2016-07-22 81 views
2

所以我有一個Django彈性魔豆的應用程序,就像這樣一個功能:在彈性跑cron作業青苗

  • 下載文件
  • 解析文件,運行到API的一些通話與數據從文件
  • 更新EB實例的數據庫與新的數據

在我剛剛建立了一個本地cron作業的測試實例。我剛剛在我的Django應用程序的特定URL上調用了wget,它將運行該命令。

我的問題是如何在多實例Elastic Beanstalk應用程序中處理此問題。我的EB應用程序只有一個實例應該運行這個命令。我想避免數據庫上的競爭條件和多個實例對外部API的冗餘調用。即只有一個實例應該寫入數據記錄。

但是,谷歌搜索顯示設置cron工作是尷尬的,特別是如果你像EB的新EB。最有希望的探測方法似乎是cron.yaml方法,但似乎沒有一個例子可以在我看到的網絡上的任何位置設置cron工作環境。

我的理解是:

  • 您在您的EB項目的根cron.yaml文件。
  • 部署項目
  • cron作業自動設置在工作環境(?)中。
  • 您定義的命令在指定的時間運行。

我的問題是你如何確保只有一個實例將運行此命令?我有關於cron.yaml如何工作的原因或者我是否缺少某些東西

回答

2

只有一個實例會運行該命令,因爲cron作業實際上並未在cron守護進程中運行。

有幾個概念可以幫助您快速理解亞馬遜的Elastic Beanstalk思維模式。

  • 彈性魔豆環境必須選擇其中必有永遠只能是一個領導者的實例(它必須是一個健康的實例等)。
  • 工作人員環境通過SQS(簡單隊列服務)隊列分配工作。
  • 一旦從隊列中讀取消息,它將被視爲「正在進行中」,直到worker返回200或請求超時/失敗。在第一種情況下,消息被刪除,在後一種情況下,它重新進入隊列。 (Redrive策略可以確定消息在發送到死信隊列之前可以失敗的次數)
  • 在飛行中,消息不能再次讀取(除非返回)。

在隊列中的消息是通過在工人環境實例的一個在一個時間拾起只有一次。

現在cron.yaml文件實際上只是告訴領導在隊列中用特殊屬性在隊列中創建一條消息。當它發現此消息時,它僅作爲對指定URL的POST請求分派給一個實例。

當我在工作環境中使用Django時,我創建了一個cron應用程序,其視圖映射到我想要的操作。例如,如果我想定期輪詢Facebook的終點,我可能有一個路徑/cron/facebook/poll/它調用了views.py

如果我有一個cron.yaml如下這樣一個poll_facebook()功能,它會輪詢的Facebook每小時一次:

version: 1 
cron: 
- name: "pollfacebook" 
    url: "/cron/facebook/poll/" 
    schedule: "0 * * * *" 
+0

經過多次試驗和錯誤後,最終發現了這一點,它很高興爲其他人解決了這個問題。 – GreenGodot