天天看點

storm基礎概念storm基礎概念

storm基礎概念

  • storm基礎概念
    • 1. 拓撲(Topologies)
    • 2. 流(Streams)
    • 3. 資料源(Spouts)
    • 4. 資料流處理元件(Bolts)
    • 5.資料流分組(Stream groupings)
    • 6.可靠性
    • 7.任務(Tasks)
    • 8.工作程序(Workers)

storm基礎概念

以官網的結構圖為例子

storm基礎概念storm基礎概念

storm用來幹什麼這裡就不說了,主要說下storm的一些基礎知識。官宣連接配接:http://storm.apache.org/releases/1.2.2/Concepts.html

原文翻譯:

http://ifeve.com/storm-concepts/

其實官方文檔已經介紹的非常詳細了,這裡隻是對某些比較晦澀的地方進行一些說明。

Storm 系統中包含以下幾個基本概念:

拓撲(Topologies)

流(Streams)

資料源(Spouts)

資料流處理元件(Bolts)

資料流分組(Stream groupings)

可靠性(Reliability)

任務(Tasks)

工作程序(Workers)

1. 拓撲(Topologies)

Storm 的拓撲是對實時計算應用邏輯的封裝,它的作用與 MapReduce 的任務(Job)很相似,差別在于 MapReduce 的一個 Job 在得到結果之後總會結束,而拓撲會一直在叢集中運作,直到你手動去終止它。拓撲還可以了解成由一系列通過資料流(Stream Grouping)互相關聯的 Spout 和 Bolt 組成的的拓撲結構。Spout 和 Bolt 稱為拓撲的元件(Component)。

2. 流(Streams)

資料流(Streams)是 Storm 中最核心的抽象概念。一個資料流指的是在分布式環境中并行建立、處理的一組元組(tuple)的無界序列。資料流可以由一種能夠表述資料流中元組的域(fields)的模式來定義。在預設情況下,元組(tuple)包含有整型(Integer)數字、長整型(Long)數字、短整型(Short)數字、位元組(Byte)、雙精度浮點數(Double)、單精度浮點數(Float)、布爾值以及位元組數組等基本類型對象。當然,你也可以通過定義可序列化的對象來實作自定義的元組類型。

在聲明資料流的時候需要給資料流定義一個有效的 id。不過,由于在實際應用中使用最多的還是單一資料流的 Spout 與 Bolt,這種場景下不需要使用 id 來區分資料流,是以可以直接使用 OutputFieldsDeclarer來定義“無 id”的資料流。實際上,系統預設會給這種資料流定義一個名為“default”的 id。

3. 資料源(Spouts)

資料源(Spout)是拓撲中資料流的來源。一般 Spout 會從一個外部的資料源讀取元組然後将他們發送到拓撲中。根據需求的不同,Spout 既可以定義為可靠的資料源,也可以定義為不可靠的資料源。一個可靠的 Spout 能夠在它發送的元組處理失敗時重新發送該元組,以確定所有的元組都能得到正确的處理;相對應的,不可靠的 Spout 就不會在元組發送之後對元組進行任何其他的處理。

一個 Spout 可以發送多個資料流。為了實作這個功能,可以先通過 OutputFieldsDeclarer 的 declareStream 方法來聲明定義不同的資料流,然後在發送資料時在 SpoutOutputCollector 的 emit 方法中将資料流 id 作為參數來實作資料發送的功能。

Spout 中的關鍵方法是 nextTuple。顧名思義,nextTuple 要麼會向拓撲中發送一個新的元組,要麼會在沒有可發送的元組時直接傳回。需要特别注意的是,由于 Storm 是在同一個線程中調用所有的 Spout 方法,nextTuple 不能被 Spout 的任何其他功能方法所阻塞,否則會直接導緻資料流的中斷(關于這一點,阿裡的 JStorm 修改了 Spout 的模型,使用不同的線程來處理消息的發送,這種做法有利有弊,好處在于可以更加靈活地實作 Spout,壞處在于系統的排程模型更加複雜,如何取舍還是要看具體的需求場景吧)。

Spout 中另外兩個關鍵方法是 ack 和 fail,他們分别用于在 Storm 檢測到一個發送過的元組已經被成功處理或處理失敗後的進一步處理。注意,ack 和 fail 方法僅僅對上述“可靠的” Spout 有效。

簡單的來講就是要處理的資料的源頭,storm官方将其形象的比喻為水龍頭。

4. 資料流處理元件(Bolts)

拓撲中所有的資料處理均是由 Bolt 完成的。通過資料過濾(filtering)、函數處理(functions)、聚合(aggregations)、聯結(joins)、資料庫互動等功能,Bolt 幾乎能夠完成任何一種資料處理需求。

一個 Bolt 可以實作簡單的資料流轉換,而更複雜的資料流變換通常需要使用多個 Bolt 并通過多個步驟完成。例如,将一個微網誌資料流轉換成一個趨勢圖像的資料流至少包含兩個步驟:其中一個 Bolt 用于對每個圖檔的微網誌轉發進行滾動計數,另一個或多個 Bolt 将資料流輸出為“轉發最多的圖檔”結果(相對于使用2個Bolt,如果使用3個 Bolt 你可以讓這種轉換具有更好的可擴充性)。

Bolt 可以将其了解為一個具有處理功能的spout,它既可以處理資料,也可以向後面的Bolt 發射資料。與spout一樣Bolt 也有ack 和 fail 方法,用于可靠的資料處理

5.資料流分組(Stream groupings)

為拓撲中的每個 Bolt 的确定輸入資料流是定義一個拓撲的重要環節。資料流分組定義了在 Bolt 的不同任務(tasks)中劃分資料流的方式。

在 Storm 中有八種内置的資料流分組方式(原文有誤,現在已經已經有八種分組模型——譯者注),而且你還可以通過CustomStreamGrouping 接口實作自定義的資料流分組模型。這八種分組分時分别為:

  1. 随機分組(Shuffle grouping):這種方式下元組會被盡可能随機地配置設定到 Bolt 的不同任務(tasks)中,使得每個任務所處理元組數量能夠能夠保持基本一緻,以確定叢集的負載均衡。
  2. 域分組(Fields grouping):這種方式下資料流根據定義的“域”來進行分組。例如,如果某個資料流是基于一個名為“user-id”的域進行分組的,那麼所有包含相同的“user-id”的元組都會被配置設定到同一個任務中,這樣就可以確定消息處理的一緻性。
  3. 部分關鍵字分組(Partial Key grouping):這種方式與域分組很相似,根據定義的域來對資料流進行分組,不同的是,這種方式會考慮下遊 Bolt 資料處理的均衡性問題,在輸入資料源關鍵字不平衡時會有更好的性能。感興趣的讀者可以參考這篇論文,其中詳細解釋了這種分組方式的工作原理以及它的優點。
  4. 完全分組(All grouping):這種方式下資料流會被同時發送到 Bolt 的所有任務中(也就是說同一個元組會被複制多份然後被所有的任務處理),這種情況會使得資料被重複處理,使用這種分組方式要特别小心。(有點類似于消息隊列裡面的廣播概念)
  5. 全局分組(Global grouping):這種方式下所有的資料流都會被發送到 Bolt 的同一個任務中,也就是 id 最小的那個任務,也就是将所有資料流彙總到一個bolt。
  6. 非分組(None grouping):使用這種方式說明你不關心資料流如何分組。目前這種方式的結果與随機分組完全等效,不過未來 Storm 社群可能會考慮通過非分組方式來讓 Bolt 和它所訂閱的 Spout 或 Bolt 在同一個線程中執行。
  7. 直接分組(Direct grouping):這是一種特殊的分組方式。使用這種方式意味着元組的發送者可以指定下遊的哪個任務可以接收這個元組。隻有在資料流被聲明為直接資料流時才能夠使用直接分組方式。使用直接資料流發送元組需要使用 OutputCollector 的其中一個 emitDirect 方法。Bolt 可以通過 TopologyContext 來擷取它的下遊消費者的任務 id,也可以通過跟蹤 OutputCollector 的 emit 方法(該方法會傳回它所發送元組的目标任務的 id)的資料來擷取任務 id。
  8. 本地或随機分組(Local or shuffle grouping):如果在源元件的 worker 程序裡目标 Bolt 有一個或更多的任務線程,元組會被随機配置設定到那些同程序的任務中。換句話說,這與随機分組的方式具有相似的效果。

6.可靠性

Storm 可以通過拓撲來確定每個發送的元組都能得到正确處理。通過跟蹤由 Spout 發出的每個元組構成的元組樹可以确定元組是否已經完成處理。每個拓撲都有一個“消息延時”參數,如果 Storm 在延時時間内沒有檢測到元組是否處理完成,就會将該元組标記為處理失敗,并會在稍後重新發送該元組。

為了充分利用 Storm 的可靠性機制,你必須在元組樹建立新結點的時候以及元組處理完成的時候通知 Storm。這個過程可以在 Bolt 發送元組時通過 OutputCollector 實作:在 emit 方法中實作元組的錨定(Anchoring),同時使用 ack 方法表明你已經完成了元組的處理。

簡單點來講就是在emit一個,必須對發射的元組進行錨定(可以想象為與一個id相對應),然後發射成功時調用ack方法進行确認,失敗是調用fail方法通知spout一遍重新發送該條元組。後面會在例子中實作一個可靠的wordcount例子來加以說明。

7.任務(Tasks)

在 Storm 叢集中每個 Spout 和 Bolt 都由若幹個任務(tasks)來執行。每個任務都與一個執行線程相對應。資料流分組可以決定如何由一組任務向另一組任務發送元組。你可以在 TopologyBuilder 的 setSpout 方法和 setBolt 方法中設定 Spout/Bolt 的并行度。

8.工作程序(Workers)

拓撲是在一個或多個工作程序(worker processes)中運作的。每個工作程序都是一個實際的 JVM 程序,并且執行拓撲的一個子集。例如,如果拓撲的并行度定義為300,工作程序數定義為50,那麼每個工作程序就會執行6個任務(程序内部的線程)。Storm 會在所有的 worker 中分散任務,以便實作叢集的負載均衡。

繼續閱讀