1.寫在前面

1.1需求來源

最近有一個需求,假設(shè)我們有很多任務(wù)需要定時執(zhí)行甚至定時重復(fù)運行,并且其中有一些任務(wù)之間可能存在控制依賴和/或數(shù)據(jù)依賴,甚至我們希望可以利用一些原子任務(wù)去組成一個更大的任務(wù)。

所以我們需要有一個工具可以將這些任務(wù)管理起來:1)解決依賴問題;2)將能并發(fā)的任務(wù)最大化地并發(fā)起來;3)使用簡單,只需填寫配置文件,不需要寫任何代碼即可讓一堆任務(wù)有序地Run起來;4)能夠正確調(diào)度這些任務(wù)的順序;5)may be more。

我調(diào)研了一些已經(jīng)存在的任務(wù)執(zhí)行引擎,包括FStack。然而試用了一下FStack,發(fā)現(xiàn)我不會用,這就很尷尬了。
報著“殺雞焉用牛刀”的想法,于是最終花了幾天自己寫了一個可實際運行的工具,即panguan(判官)。

1.2名字來源

這個任務(wù)執(zhí)行引擎被命名為“判官”,就是想給人一種不明覺厲的裝X氣質(zhì)。

據(jù)百度百科記載,傳說中陰曹地府中的判官判處人的輪回生死,對壞人進行懲罰,對好人進行獎勵。而該任務(wù)執(zhí)行引擎的主要工作是調(diào)度任務(wù)的順序和生存周期,對執(zhí)行成功和失敗的任務(wù)進行處理。感覺這個名字很有這個場景的氣質(zhì),于是配置任務(wù)屬性的配置文件就順便被命名為shengsibu.xml了。

1.3目前支持的特性

  1. 通過XML文件配置任務(wù)。
  2. 支持多任務(wù)同時運行并且互不干擾。
  3. 支持單個任務(wù)由多個存在數(shù)據(jù)依賴和控制依賴或者可以并行執(zhí)行的子任務(wù)組成。子任務(wù)可以繼續(xù)由多個子任務(wù)組成,由此可以遞歸成為一棵復(fù)雜的任務(wù)樹。
  4. 能夠調(diào)度各種復(fù)雜的任務(wù)場景的任務(wù)的順序,使其并發(fā)最大化。
  5. 支持立即執(zhí)行、定時和重復(fù)執(zhí)行。
  6. 對任務(wù)進行超時檢測。
  7. 展示每一個任務(wù)的當(dāng)前任務(wù)狀態(tài)和運行時間。
  8. 支持原子任務(wù)去調(diào)用python和shell的腳本。另外可以不實際去執(zhí)行腳本而讓程序模擬結(jié)果,目前返回時間是二項分布~(100,0.05)的隨機結(jié)果,是否執(zhí)行成功是p為0.88的伯努利分布的隨機結(jié)果。

2.工程實踐

以下主要簡要介紹一些實踐中的想法和思路。

2.1異步引擎加線程池

為了支持定時機制、多任務(wù)、任務(wù)組裝、任務(wù)依賴等特性,同步的做法顯得力不從心,當(dāng)然也可能是我水平差導(dǎo)致寫不出來。于是在這里優(yōu)先采用了異步引擎加線程池的方案。相對于同步的做法,異步的做法開銷更小;然而會導(dǎo)致程序的實現(xiàn)難度增加,也更加難以理解。

我們需要:1)一個異步引擎;2)兩個不同方向的線程安全的消息隊列,一個是請求MQ,一個是返回MQ;3)一個工作線程池。
異步引擎將每個原子任務(wù)派發(fā)到請求MQ中,線程中的工作線程監(jiān)聽請求MQ,執(zhí)行完后插入另一個返回MQ中。異步引擎從返回取回結(jié)果。

如下圖所示。

我們可以繼續(xù)推廣至一個多機的版本,如下圖。

Agent同時監(jiān)聽兩個消息隊列(一個自身的MQ和一個Center的請求MQ):Agent從Center拉取消息的模式,可以自動實現(xiàn)負(fù)載均衡;Center推給Agent的模式,可以指定將任務(wù)派發(fā)至某個機器,以此提高執(zhí)行效率。原因可能是這個任務(wù)距離數(shù)據(jù)目標(biāo)端的物理距離更近。

2.2對任務(wù)進行抽象

2.2.1使用DAG去定義

網(wǎng)友評論