任務分發,請使用gearman

  1. 一般,多語言多系統之間的集成是個大問題,通常來講,人們多半會採用WebService的方式來處理此類集成問題,但無論採用何種風格的 WebService,如RPC風格,或者REST風格,其自己都有必定的複雜性。相比之下,Gearman也能實現相似的做用,並且更簡單易用。  
  2. 一個Gearman請求的處理過程涉及三個角色:Client -> Job -> Worker。  
  3. Client:請求的發起者,能夠是C,PHP,Perl,MySQL UDF等等。  
  4. Job:請求的調度者,用來負責協調把Client發出的請求轉發給合適的Work。  
  5. Worker:請求的處理者,能夠是C,PHP,Perl等等。  
  6. 由於Client,Worker並不限制用同樣的語言,因此有利於多語言多系統之間的集成  
  7.   
  8.   
  9. gearman另外一個應用方面是負載分擔,你能夠將worker放在不一樣的服務器(或者一些列服務器)上,好比你的php程序須要圖片轉換,可是不但願本 地服務器有太多的這樣圖片轉換的進程,那麼你能夠創建一系列服務器,在上面加載worker處理圖片轉換。這樣你的web服務器將不受圖片轉換的影響,同 時你獲得了負載均衡的功能,由於jobserver會在請求到來的時候,將這個請求發給空閒的worker.一樣對於多核的服務器,你能夠在同一機器上創 建一樣數目的worker.你可能擔憂,jobserver處於一箇中心,那麼這會是一個單點的瓶頸,若是死了,會怎麼樣?對於這樣的狀況,你能夠運行多 個jobserver。這樣若是一個jobserver down了,client和worker會自動遷移到另外一臺jobserver上。 


從08年開始,所謂的雲計算開始流行起來,什麼分佈式計算模型、分佈式消息隊列、分佈式存儲系統各類新鮮事物。

gearman,從名字上看叫作「齒輪工」,就是經過齒輪把不一樣的組件組合在一塊兒。一般,多語言多系統之間的集成是項目開發中一個比較頭疼的問題。通常會採用RPC風格或者是REST風格的WebService。可是總感受比較麻煩。gearman就應運而生了,做爲一個任務分發架構,它可以輕鬆的將前端的任務經過Job Server分發給後端的Worker處理。Gearman請求的處理過程涉及三個角色:Client -> Job Server -> Worker。

Client:請求的發起者,能夠是C,PHP,Perl,MySQL UDF等等。
Job Server:請求的調度者,用來負責協調把Client發出的請求轉發給合適的Worker。
Worker:請求的處理者,能夠是C,PHP,Perl等等。

工做原理圖:

工做流:

由於Client,Worker並不限制用同樣的語言,因此有利於多語言多系統之間的集成。
甚至咱們經過增長更多的Worker,能夠很方便的實現應用程序的分佈式負載均衡架構。

集羣架構: php


關於gearman的分佈式任務處理:
1. 其實每個任務處理的時間並無下降,相反會稍稍有所增長,主要是數據在網絡上傳輸的一些時間。
2. 前端Client(一般是web服務器)的負載下降了,可是轉移到了後端Worker上。
計算不可能憑空消失,只不過從一臺機器轉移到了另一臺機器。

3. 同步方式的話,前端Client(一般是Web服務器)等待的時間與後端Worker的數量與當前任務數有關。若是任務數量<=Worker數量,前端Client等待的時間約等於一個任務處理的時間。
可是當任務數>=Worker數量時,就會出現某些Client等待的狀況,某個Client只有等到一個空閒的Worker,纔會將任務交給它進行處理。

設想一下,在任務數<=Worker數量的時候,使用gearman是能夠提升響應時間的。若是採用單機話,N個任務仍是在一臺機器上運行,每一個任務須要

如今有N個任務(Client),M個Worker,每一個任務執行時間爲t。若是不是用gearman的話,須要的時間爲N*t,平均等待時間爲N*t/2。
若是使用了gearman的話,而且N<=M,須要的時間爲t,平均等待時間爲t;若是N>M的話,須要的時間爲(N/M)*t or (N/M+1)*t。

test.sh
#!/bin/sh
sleep 10
echo "TEST"

開啓2個Worker
./gearman -w -f test /home/wangyao/test.sh

開啓3個Client:
date;./gearman -f test;date
三個結果分別爲:
--------------------------------------------
Wed Mar 17 14:41:31 CST 2010
TEST 
Wed Mar 17 14:41:41 CST 2010
--------------------------------------------
Wed Mar 17 14:41:32 CST 2010
TEST 
Wed Mar 17 14:41:42 CST 2010
--------------------------------------------
Wed Mar 17 14:41:34 CST 2010
TEST 
Wed Mar 17 14:41:51 CST 2010
--------------------------------------------
能夠看出前兩個Client的任務都用了10s,可是第3個任務卻花了17s。主要在於當第3個任務執行的時候,沒有空閒的Worker執行任務,必須等到一個Worker空閒下來,最早空閒的Worker要在14:41:41,在這個時刻執行第3個任務,如今已通過去了7s,再須要10s完成任務,所以第3個任務最終用了17s。

4. 異步方式的話,任務交給後端Worker後,前端Client就返回了,這樣用戶體驗比較好。可是,存在任務執行失敗或者是任務結果反饋的問題。
通常採用數據庫做爲存儲,將任務執行的狀態信息、結果等存入數據庫;前端Client按期檢查數據庫中的結果,再進一步進行操做,是向用戶呈現結果仍是從新執行任務。

一個應用實例:
Client將log發送到專門的log服務器:
tail -f access_log | gearman -h host -f logger

可能會有多個log服務器,log服務器將接受到的log信息寫入到一個文件中:
gearman -w -h host -f logger > log_file

進行分佈式grep,須要在每臺log服務器設置一個function:
gearman -w host -f logger1 ./dgrep.sh

#!/bin/sh
read pattern
grep $pattern log_file

相應的在其餘log服務器上建立logger2,logger3等。

如今,日誌已經在日誌服務器上了。咱們在其餘機器上,想對日誌進行分佈式的grep。只須要做爲一個client,調用worker logger一、logger二、logger3等。
gearman -h host -f logger1 -f logger2 -f logger3 KEYWORD 
這就能夠能夠在全部的機器上grep KEYWORD了。

這種方法不是很靈活,每臺機器設置一個func,對上層不透明。

整體來看,gearman適合於那種task數量遠遠大於worker數量的應用。理論上來看,將計算開銷轉移到Worker上,從而實現任務的併發執行,表現爲client計算負載減輕,用戶的等待時間減小。
對Client而言是task,對於Worker而言是job。

後記:管理工具 前端

Gearman-Monitor git

GearmanManager github

相關文章
相關標籤/搜索