本文是學習時的自我總結,用於往後溫習。若有錯誤還望諒解,不吝賜教前端
此處附上部份內容所出博客:http://blog.csdn.net/ymh198816/article/details/51998085數據庫
Flume+Kafka+Storm+Redis實時分析系統基本架構編程
1) 整個實時分析系統的架構是後端
2) 先由電商系統的訂單服務器產生訂單日誌,緩存
3) 而後使用Flume去監聽訂單日誌,安全
4) 並實時把每一條日誌信息抓取下來並存進Kafka消息系統中,服務器
5) 接着由Storm系統消費Kafka中的消息,網絡
6) 同時消費記錄由Zookeeper集羣管理,這樣即便Kafka宕機重啓後也能找到上次的消費記錄,接着從上次宕機點繼續從Kafka的Broker中進行消費。可是因爲存在先消費後記錄日誌或者先記錄後消費的非原子操做,若是出現恰好消費完一條消息並還沒將信息記錄到Zookeeper的時候就宕機的相似問題,或多或少都會存在少許數據丟失或重複消費的問題, 其中一個解決方案就是Kafka的Broker和Zookeeper都部署在同一臺機子上。架構
7) 接下來就是使用用戶定義好的Storm Topology去進行日誌信息的分析並輸出到Redis緩存數據庫中(也能夠進行持久化),最後用Web APP去讀取Redis中分析後的訂單信息並展現給用戶。併發
之因此在Flume和Storm中間加入一層Kafka消息系統,就是由於在高併發的條件下, 訂單日誌的數據會井噴式增加,若是Storm的消費速度(Storm的實時計算能力那是最快之一,可是也有例外, 並且聽說如今Twitter的開源實時計算框架Heron比Storm還要快)慢於日誌的產生速度,加上Flume自身的侷限性,必然會致使大量數據滯後並丟失,因此加了Kafka消息系統做爲數據緩衝區,並且Kafka是基於log File的消息系統,也就是說消息可以持久化在硬盤中,再加上其充分利用Linux的I/O特性,提供了可觀的吞吐量。架構中使用Redis做爲數據庫也是由於在實時的環境下,Redis具備很高的讀寫速度。
Flume和Kafka對比
(1)kafka和flume都是日誌系統。kafka是分佈式消息中間件,自帶存儲,提供push和pull存取數據功能。flume分爲agent(數據採集器),collector(數據簡單處理和寫入),storage(存儲器)三部分,每一部分都是能夠定製的。好比agent採用RPC(Thrift-RPC)、text(文件)等,storage指定用hdfs作。
(2)kafka作日誌緩存應該是更爲合適的,可是 flume的數據採集部分作的很好,能夠定製不少數據源,減小開發量。因此比較流行flume+kafka模式,若是爲了利用flume寫hdfs的能力,也能夠採用kafka+flume的方式。
Flume
1) 可靠性
當節點出現故障時,日誌可以被傳送到其餘節點上而不會丟失。Flume提供了三種級別的可靠性保障,從強到弱依次分別爲:end-to-end(收到數據 agent首先將event寫到磁盤上,當數據傳送成功後,再刪除;若是數據發送失敗,能夠從新發送),Store on failure(這也是scribe採用的策略,當數據接收方crash時,將數據寫到本地,待恢復後,繼續發送),Best effort(數據發送到接收方後,不會進行確認)
2) 可擴展性
Flume採用了三層架構,分別問agent,collector和storage,每一層都可以水平擴展。其中,全部agent和collector由 master統一管理,這使得系統容易監控和維護,且master容許有多個(使用ZooKeeper進行管理和負載均衡),這就避免了單點故障問題。
3) 可管理性
全部agent和colletor由master統一管理,這使得系統便於維護。用戶能夠在master上查看各個數據源或者數據流執行狀況,且能夠對各個數據源配置和動態加載。
4) 功能可擴展性
用戶能夠根據須要添加本身的agent,colletor或者storage。
3. Flume架構
Flume採用了分層架構,由三層組成:agent,collector和storage。其中,agent和collector均由兩部分組成:source和sink,source是數據來源,sink是數據去向。
Flume的核心是Agent進程,是一個運行在服務器節點的Java進程。
agent:將數據源的數據發送到collector
collector:將多個agent的數據彙總後,加載到storage。它的source和sink與agent相似
storage:存儲系統,能夠是一個普通file,也能夠是HDFS,Hive,HBase等。
source(數據源):用於收集各類數據
channel:臨時存放數據,能夠存放在memory、jdbc、file等
sink:把數據發送到目的地,如HDFS、HBase等
Flume傳輸數據的基本單位是event,事務保證是在event級別進行的,event將傳輸的數據進行封裝
只有在sink將channel中的數據成功發送出去以後,channel纔會將臨時數據進行刪除,這種機制保證了數據傳輸的可靠性與安全性。
4. Flume的廣義用法
Flume支持多級Flume的Agent,即sink能夠將數據寫到下一個Agent的source中,
且Flume支持扇入(source能夠接受多個輸入)、扇出(sink能夠將數據輸出多個目的地)
一個複雜的例子以下:有6個agent,3個collector,全部collector均將數據導入HDFS中。agent A,B將數據發送給collector A,agent C,D將數據發送給collectorB,agent C,D將數據發送給collectorB。同時,爲每一個agent添加end-to-end可靠性保障,若是collector A出現故障時,agent A和agent B會將數據分別發給collector B和collector C。
Kafka
持久性消息:不會丟失任何信息,提供穩定的TB級消息存儲
高吞吐量:Kafka設計工做在商用硬件上,提供每秒百萬的消息
分佈式架構,可以對消息分區
實時:消息由生產者線程生產出來馬上被消費者看到,數據在磁盤上的存取代價爲O(1)
3. Kafka架構
Kafka其實是一個消息發佈訂閱系統。Kafka將消息以Topic爲單位進行概括,將向Topic發佈消息的程序做爲producer,預約消息的做爲consumer。Kafka以集羣方式運行,能夠由一個或多個服務組成,每一個服務叫作一個broker。一旦有新的關於某topic的消息,broker會傳遞給訂閱它的全部consumer。 在kafka中,消息是按topic組織的,而每一個topic又會分爲多個partition,這樣便於管理數據和進行負載均衡。同時,它也使用了 zookeeper進行負載均衡。
1) Producer
向broker發送數據。
Kafka提供了兩種producer接口:
a) low_level接口,用於向特定的broker的某個topic下的某個partition發送數據;
b) high level接口,支持同步/異步發送數據,基於zookeeper的broker自動識別和負載均衡(基於Partitioner)。producer能夠經過zookeeper獲取可用的broker列表,也能夠在zookeeper中註冊listener,該listener在添加刪除broker,註冊新的topic或broker註冊已存在的topic時被喚醒:當producer得知以上時間時,可根據須要採起必定的行動。
2) Broker
Broker採起了多種策略提升數據處理效率,包括sendfile和zero copy等技術。
3) Consumer
將日誌信息加載到中央存儲系統上。
kafka提供了兩種consumer接口:
a) low level接口:維護到某一個broker的鏈接,而且這個鏈接是無狀態的,每次從broker上pull數據時,都要告訴broker數據的偏移量。
b) high level接口:隱藏了broker的細節,容許consumer從broker上push數據而沒必要關心網絡拓撲結構。更重要的是,對於大部分日誌系統而言,consumer已經獲取的數據信息都由broker保存,而在kafka中,由consumer本身維護所取數據信息
4. Kafka消息發送流程
1) Producer根據指定的partition方法,將消息發佈到指定topic的partition裏面
2) 集羣接收到Producer發送的消息後,將其持久化到硬盤,並保留消息指定時長,而不關注消息是否被消費。
3) Consumer從kafka集羣pull數據,並控制獲取消息的offset
詳細過程:
Kafka是一個分佈式的高吞吐量的消息系統,同時兼有點對點和發佈訂閱兩種消息消費模式。
Kafka主要由Producer,Consumer和Broker組成。Kafka中引入了一個叫「topic」的概念,用來管理不一樣種類的消息,不一樣類別的消息會記錄在到其對應的topic池中。而這些進入到topic中的消息會被Kafka寫入磁盤的log文件中進行持久化處理。對於每個topic裏的消息log文件,Kafka都會對其進行分片處理。而每個消息都會順序寫入中log分片中,而且被標上「offset」的標量來表明這條消息在這個分片中的順序,而且這些寫入的消息不管是內容仍是順序都是不可變的。因此Kafka和其它消息隊列系統的一個區別就是它能作到分片中的消息是能順序被消費的,可是要作到全局有序仍是有侷限性的,除非整個topic只有一個log分片。而且不管消息是否有被消費,這條消息會一直保存在log文件中,當留存時間足夠長到配置文件中指定的retention的時間後,這條消息纔會被刪除以釋放空間。對於每個Kafka的Consumer,它們惟一要存的Kafka相關的元數據就是這個「offset」值,記錄着Consumer在分片上消費到了哪個位置。一般Kafka是使用Zookeeper來爲每個Consumer保存它們的offset信息,因此在啓動Kafka以前須要有一個Zookeeper集羣;並且Kafka默認採用的是先記錄offset再讀取數據的策略,這種策略會存在少許數據丟失的可能。不過用戶能夠靈活設置Consumer的「offset」的位置,在加上消息記錄在log文件中,因此是能夠重複消費消息的。log的分片和它們的備份會分散保存在集羣的服務器上,對於每個partition,在集羣上都會有一臺這個partition存在的服務器做爲leader,而這個partitionpartition的其它備份所在的服務器作爲follower,leader負責處理關於這個partition的全部請求,而follower負責這個partition的其它備份的同步工做,當leader服務器宕機時,其中一個follower服務器就會被選舉爲新的leader。
數據的傳遞方式
1) Socket:最簡單的交互方式,典型的c/s交互模式。傳輸協議能夠是TCP/UDP
優勢:易於編程,Java有不少框架,隱藏了細節;容易控制權限,經過https,使得安全性提升;通用性強
缺點:服務器和客戶端必須同時在線;當傳輸數據量比較大的時候,嚴重佔用網絡帶寬,致使鏈接超時
2) FTP/文件共享服務器方式:適用於大數據量的交互
優勢:數據量大時,不會超時,不佔用網絡帶寬;方案簡單,避免網絡傳輸、網絡協議相關概念
缺點:不適合作實時類的業務;必須有共同的服務器,可能存在文件泄密;必須約定文件數據的格式
3) 數據庫共享數據方式:系統A、B經過鏈接同一個數據庫服務器的同一張表進行數據交換
優勢:使用同一個數據庫,使得交互更簡單,交互方式靈活,可更新,回滾,由於數據庫的事務,交互更可靠
缺點:當鏈接B的系統愈來愈多,會致使每一個系統分配到的鏈接不會不少;
通常來講,兩個公司的系統不會開放本身的數據庫給對方,影響安全性
4) 消息方式:Java消息服務(Java Message Service)是message數據傳輸的典型的實現方式
優勢:JMS定義了規範,有不少消息中間件可選;消息方式比較靈活,可採起同步、異步、可靠性的消息處理
缺點:JMS相關的學習對開發有必定的學習成本;在大數據量的狀況下,可能形成消息積壓、延遲、丟失甚至中間件崩潰
1.消息隊列
任何軟件工程遇到的問題均可以經過增長一箇中間層來解決
消息隊列是在消息的傳輸過程當中保存消息的容器。主要目的是提供路由並保證消息的傳遞,若是發送消息時接收者不可用,消息隊列會保留消息,直到能夠成功地傳遞它。
2. 消息中間件做用
系統解耦:服務B出現問題不會影響服務A
削峯填谷:對請求壓力實現削峯填谷,下降系統峯值壓力
數據交換:無需暴露企業A和B的內網就能夠實現數據交換
異步通知:減小前端和後端服務之間大量沒必要要的輪詢請求
定時任務:如生成付款檢查任務,延遲30分鐘