Dryad 微軟的分布式運算框架

jopen 10年前發布 | 33K 次閱讀 分布式 分布式/云計算/大數據

Dryad的論文是微軟早在2007年就發布的,Tez的核心思想來源于Dryad,差不多可以算是Dryad的開源實現吧。最近正好看到幾個有趣的項目是基于Tez實現的,于是順便追本溯源,學習了一下Dryad的理論基礎

 

==目標問題 ==

 

Dryad的 設計目標和當時先后出現的各種分布式運算框架一樣,是為了簡化大規模分布式編程的難度,提供給用戶一個簡單通用的分布式運算框架。和其它分布式運算框架解 決的問題類似,不外乎就是用戶不需要考慮分布式運算所涉及的眾多繁瑣的問題,例如資源分配,并發調度,系統容錯等等,而只需要關注核心運算邏輯。

 

==核心思想 ==

 

按照官方定義,Dryad是一個通用的粗顆粒度的分布式計算和資源調度引擎,這里所說的粗顆粒度,自然指的是針對批量數據進行處理的這種應用模式,當然批處理的粒度可大可小。

 

Dryad的核心數據模型由Vertex計算節點和Channel數據通道兩部分組成,用戶通過實現自定義的Vertex節點來執行定制的運算邏輯,而節點之間通過各種形式的數據通道傳輸數據,用戶的運算邏輯本身通常是順序執行的,而與分布式相關的邏輯則由Dryad框架來實現。

 

d1.png

 

如圖所示的是Dryad的系統架構框圖。Dryad的作業管理模塊JM在應用程序內部維護了一個基于DAG圖模型的計算節點依賴關系圖,作業管理模塊通過命名服務器NS來獲取可用的服務器列表,而后通過在這些服務器上運行的守護進程Daemon來調度和執行計算節點Vertex。各個計算節點之間通過例如文件,管道,網絡等形式的數據通道交換數據。

 

表面上看,從整體的概念來說,DryadMapReduce十分相似,所不同的就是MapReduce的用戶邏輯分為MapReduce兩個階段,在Dryad里就只有不分階段的Vertex一個概念。不過這一點恰恰就是它與MapReduce區別的關鍵。

 

從用戶使用的角度來說,MapReduce強制定義了MapReduce兩個階段,以及兩階段之間的數據輸入輸出格式。用戶程序通過套用這種模型來抽象自身的運算邏輯,帶來的好處是,簡化了用戶編程接口,降低編程難度,同時在這種模型的基礎上MapReduce框架可以自動完成各種調度優化和容錯處理工作。但是固定的編程模型自然也就在一定程度上限制了它的通用性,比如MR模型中所有的計算節點只能接受統一格式的一組輸入數據,也只能輸出一組數據,無論是否需要,用戶邏輯都必須由匹配的MapReduce階段組成等等。

 

為了具備更大的通用性,Dryad從模型上不區分運算階段,從框架的角度上也不定義各個計算節點之間的數據交換格式,而是由具體的需要相互通訊的計算節點自己處理數據的格式兼容問題。這樣做在一定程度上當然增加了用戶的編程難度,例如就可能需要針對具體計算節點的實現,編寫各種Channel數據通道的實現(當然可以通過實現一些通用的數據通道供用戶匹配使用來解決部分問題)但是帶來的好處也是顯而易見的,就是更加靈活的編程模型。

 

用戶自定義調度拓撲圖

 

Dryad的核心特性之一,是允許用戶自己構建DAG調度拓撲圖,這個特性正是基于上述的原因而具備了實現的可能性和價值。MapReduce通過隱藏調度邏輯,簡化用戶編程。與之相反,Dryad期望通過適當增加的編程復雜度,暴露給用戶更加靈活的調度編程接口,讓用戶能夠更有效的優化運行邏輯,從而達到提升程序性能的目的。

 

Dryad運行庫實現了一個簡單的圖形描述語言(graph description language)用來構建調度拓撲圖,基本的操作原語和例子如下圖所示:

 

d2.png

 

構建一個具體的DAG的例子:

 

GraphBuilder XSet =moduleX^N;

GraphBuilder DSet =moduleD^N;

GraphBuilder MSet =moduleM^(N*4);

GraphBuilder SSet =moduleS^(N*4);

GraphBuilder YSet =moduleY^N;

GraphBuilder HSet =moduleH^1;

GraphBuilder XInputs= (ugriz1 >= XSet) || (neighbor >= XSet);

GraphBuilder YInputs= ugriz2 >= YSet;

GraphBuilder XToY =XSet >= DSet >> MSet >= SSet;

for (i = 0; i

{ XToY = XToY || (SSet.GetVertex(i) >=YSet.GetVertex(i/4));}

GraphBuilder YToH =YSet >= HSet;

GraphBuilderHOutputs = HSet >= output;

GraphBuilder final =XInputs || YInputs || XToY || YToH || HOutputs;

 

上述代碼構建的DAG圖如下所示

 

d3.png

 

動態優化調度邏輯

 

Dryad的另一個特點是允許用戶動態的改變DAG調度拓撲圖,這是通過在計算節點中反饋實際所處理的數據的相關信息給作業管理模塊來實現的。之所以需要這么做,是因為在很多情況下,最優的調度拓撲結構往往取決于實際的輸入數據,中間計算結果或者當時的運行環境,因此無法在編程的時候或者程序啟動的時候提前給出最優結構。

 

d4.png

 

例如圖示的一個Aggregation類型的操作,在實際執行的時候,我們通過數據的本地性信息,可以動態的在原有的拓撲圖中(A->B)添加一層額外的計算節點(A->Z->B),比如將同一個機架上的數據匯總到同一個中間節點上作一次Aggregation,然后再提交給原拓撲圖中的后續節點處理。此外,也可以通過獲取實際的數據規模信息,動態調整各個計算節點的并發度來適配程序實際運行情況等等。

 

當然,這些動態調整的代碼邏輯本身需要用戶根據自己的業務邏輯來實現,因此在一定程度上對用戶來說也是需要付出額外的努力的

 

==實現 ==

 

Dryad的具體實現是否優化合理,實際性能如何,一方面由于它不是開源項目,另一方面我個人也不了解微軟的整套軟件體系,所有也就無從談起了,不過有空可以結合Tez這個開源版本的實現來具體分析一下。

 

==思考 ==

 

Dryad的編程模型相對于MapReduce來說固然更加靈活,但是同時也帶來了更高的編程門檻。此外,因為數據流程和交互過程更加靈活多變,大概會有很多在MapReduce里適用的各種框架級的優化工作或者通用的處理方法無法在Dryad的框架中應用,因此在易用性上勢必受到影響,而如果用戶代碼不能自己完成這些優化工作的話,應該也會對應用程序的實際性能產生一定的影響。這好比Hadoop2采用Yarn框架來支持更加通用的編程模型,但是要和MapReduce一樣,在Yarn的基礎上構建自己的模型相關的調度模塊,依然需要付出很大的努力,當然不能把Dryad的模型與Yarn簡單的資源調度模型直接對比,畢竟Dryad的編程模型還是與MapReduce一樣,屬于更高層次的概念。

 

在易用性方便,DryadDAG圖描述語言固然靈活,但在許多常用case的場合下也顯得瑣碎,比如并發度的設置等問題,許多情況下應該可以自動決定,各種常用處理流程的DAG拓撲圖也相對固定,因此也就需要一些高層封裝來簡化編程,比如構建在Dryad上的Nebula,用戶使用腳本語言的形式編程,Dryad的眾多使用細節和動態優化邏輯都被封裝在Nebula的方法操作中(例如Filter/Aggregate等),這點思想和SparkRDD的方法封裝調用DAGScheduler作業調度相關操作的思想很接近,即暴露給用戶的接口是要做什么,而不是要怎么做。

 

另外微軟的DryadLINQLINQDryad上的實現,這里暴露給用戶的也是更高層的應用接口,前面提到的各種需要解決的問題同樣交給DryadLINQ的框架來處理。

 

Paper的描述來看,當時的Dryad在并發,負載,HA等等大規模集群需要考慮的問題方面的處理方式還很簡陋,當然經過這么多年的發展,應該在這些方面會有改善和發展,目前的具體情況就不得而知了

 

Dryad的開源實現Tez所面臨的問題大概也是類似,Tez提供了各種通用的channel的實現(如針對MapReduce的應用模式的通道)來簡化用戶編程難度,但使用Tez依然比使用MapReduce要困難,Tez的穩定性和性能優化方面顯然也還有很長的路要走。而Stinger等基于Tez的上層框架顯然是希望在借助Tez在調度邏輯上提供的優化空間來提高性能的同時,通過更加高級的編程接口來保證易用性。

來自:http://blog.csdn.net/colorant/article/details/37560649

 本文由用戶 jopen 自行上傳分享,僅供網友學習交流。所有權歸原作者,若您的權利被侵害,請聯系管理員。
 轉載本站原創文章,請注明出處,并保留原始鏈接、圖片水印。
 本站是一個以用戶分享為主的開源技術平臺,歡迎各類分享!