pythonamqp
① 消息中間件(一)MQ詳解及四大MQ比較
一、消息中間件相關知識
1、概述
消息隊列已經逐漸成為企業IT系統內部通信的核心手段。它具有低耦合、可靠投遞、廣播、流量控制、扮信最終一致性等一系列功能,成為非同步RPC的主要手段之一。當今市面上有很多主流的消息中間件,如老牌的ActiveMQ、RabbitMQ,炙手可熱的Kafka,阿里巴巴自主開發RocketMQ等。
2、消息中間件的組成
2.1 Broker
消息伺服器,作為server提供消息核心服務
2.2 Procer
消息生產者,業務的發起方,負責生產消息傳輸給broker,
2.3 Consumer
消息消費者,業務的處理方,負責從broker獲取消息並進行業務邏輯處理
2.4 Topic
2.5 Queue
2.6 Message
消息體,根據不同通信協議定義的固定格式進行編碼的數據包,來封裝業務數據,實現消息的傳輸
3 消息中間件模式分類
3.1 點對點
PTP點對點:使用queue作為通信載體
說明:
消息生產者生產消息發送到queue中,然後消息消費者從queue中取出並且消費消息。
消息被消費以後,queue中不再存儲,所以消息消費者不可能消費到已經被消費的消息。 Queue支持存在多個消費者,但是對一個消息而言,只會有一個消費者可以消費。
說明:
queue實現了負載均衡,將procer生產的消息發送到消息隊列中,由多個消費者消費。但一個消息只能被一個消費者接受,當沒有消費者可用時,這個消息會被保存直到有一個可用的消費者廳謹輪。
4 消息中間件的優勢
4.1 系統解耦
交互系統之間沒有直接的調用關系,只是通過消息傳輸,故系統侵入性不強,耦合度低。
4.2 提高系統響應時間
例如原來的一套邏輯,完成支付可能涉及先修改訂單狀態、計算會員積分、通知物流配送幾個邏輯才能完成;通過MQ架構設計,就可將緊急重要(需要立刻響應晌鍵)的業務放到該調用方法中,響應要求不高的使用消息隊列,放到MQ隊列中,供消費者處理。
4.3 為大數據處理架構提供服務
通過消息作為整合,大數據的背景下,消息隊列還與實時處理架構整合,為數據處理提供性能支持。
4.4 java消息服務——JMS
Java消息服務(Java Message Service,JMS)應用程序介面是一個Java平台中關於面向消息中間件(MOM)的API,用於在兩個應用程序之間,或分布式系統中發送消息,進行非同步通信。
5 消息中間件應用場景
5.1 非同步通信
有些業務不想也不需要立即處理消息。消息隊列提供了非同步處理機制,允許用戶把一個消息放入隊列,但並不立即處理它。想向隊列中放入多少消息就放多少,然後在需要的時候再去處理它們。
5.2 解耦
降低工程間的強依賴程度,針對異構系統進行適配。在項目啟動之初來預測將來項目會碰到什麼需求,是極其困難的。通過消息系統在處理過程中間插入了一個隱含的、基於數據的介面層,兩邊的處理過程都要實現這一介面,當應用發生變化時,可以獨立的擴展或修改兩邊的處理過程,只要確保它們遵守同樣的介面約束。
5.3 冗餘
有些情況下,處理數據的過程會失敗。除非數據被持久化,否則將造成丟失。消息隊列把數據進行持久化直到它們已經被完全處理,通過這一方式規避了數據丟失風險。許多消息隊列所採用的」插入-獲取-刪除」範式中,在把一個消息從隊列中刪除之前,需要你的處理系統明確的指出該消息已經被處理完畢,從而確保你的數據被安全的保存直到你使用完畢。
5.4 擴展性
因為消息隊列解耦了你的處理過程,所以增大消息入隊和處理的頻率是很容易的,只要另外增加處理過程即可。不需要改變代碼、不需要調節參數。便於分布式擴容。
5.5 過載保護
在訪問量劇增的情況下,應用仍然需要繼續發揮作用,但是這樣的突發流量無法提取預知;如果以為了能處理這類瞬間峰值訪問為標准來投入資源隨時待命無疑是巨大的浪費。使用消息隊列能夠使關鍵組件頂住突發的訪問壓力,而不會因為突發的超負荷的請求而完全崩潰。
5.6 可恢復性
系統的一部分組件失效時,不會影響到整個系統。消息隊列降低了進程間的耦合度,所以即使一個處理消息的進程掛掉,加入隊列中的消息仍然可以在系統恢復後被處理。
5.7 順序保證
在大多使用場景下,數據處理的順序都很重要。大部分消息隊列本來就是排序的,並且能保證數據會按照特定的順序來處理。
5.8 緩沖
在任何重要的系統中,都會有需要不同的處理時間的元素。消息隊列通過一個緩沖層來幫助任務最高效率的執行,該緩沖有助於控制和優化數據流經過系統的速度。以調節系統響應時間。
5.9 數據流處理
分布式系統產生的海量數據流,如:業務日誌、監控數據、用戶行為等,針對這些數據流進行實時或批量採集匯總,然後進行大數據分析是當前互聯網的必備技術,通過消息隊列完成此類數據收集是最好的選擇。
6 消息中間件常用協議
6.1 AMQP協議
AMQP即Advanced Message Queuing Protocol,一個提供統一消息服務的應用層標准高級消息隊列協議,是應用層協議的一個開放標准,為面向消息的中間件設計。基於此協議的客戶端與消息中間件可傳遞消息,並不受客戶端/中間件不同產品,不同開發語言等條件的限制。
優點:可靠、通用
6.2 MQTT協議
MQTT(Message Queuing Telemetry Transport,消息隊列遙測傳輸)是IBM開發的一個即時通訊協議,有可能成為物聯網的重要組成部分。該協議支持所有平台,幾乎可以把所有聯網物品和外部連接起來,被用來當做感測器和致動器(比如通過Twitter讓房屋聯網)的通信協議。
優點:格式簡潔、佔用帶寬小、移動端通信、PUSH、嵌入式系統
6.3 STOMP協議
STOMP(Streaming Text Orientated Message Protocol)是流文本定向消息協議,是一種為MOM(Message Oriented Middleware,面向消息的中間件)設計的簡單文本協議。STOMP提供一個可互操作的連接格式,允許客戶端與任意STOMP消息代理(Broker)進行交互。
優點:命令模式(非topicqueue模式)
6.4 XMPP協議
XMPP(可擴展消息處理現場協議,Extensible Messaging and Presence Protocol)是基於可擴展標記語言(XML)的協議,多用於即時消息(IM)以及在線現場探測。適用於伺服器之間的准即時操作。核心是基於XML流傳輸,這個協議可能最終允許網際網路用戶向網際網路上的其他任何人發送即時消息,即使其操作系統和瀏覽器不同。
優點:通用公開、兼容性強、可擴展、安全性高,但XML編碼格式佔用帶寬大
6.5 其他基於TCP/IP自定義的協議
有些特殊框架(如:redis、kafka、zeroMq等)根據自身需要未嚴格遵循MQ規范,而是基於TCPIP自行封裝了一套協議,通過網路socket介面進行傳輸,實現了MQ的功能。
7 常見消息中間件MQ介紹
7.1 RocketMQ
阿里系下開源的一款分布式、隊列模型的消息中間件,原名Metaq,3.0版本名稱改為RocketMQ,是阿里參照kafka設計思想使用java實現的一套mq。同時將阿里系內部多款mq產品(Notify、metaq)進行整合,只維護核心功能,去除了所有其他運行時依賴,保證核心功能最簡化,在此基礎上配合阿里上述其他開源產品實現不同場景下mq的架構,目前主要多用於訂單交易系統。
具有以下特點:
官方提供了一些不同於kafka的對比差異:
https://rocketmq.apache.org/docs/motivation/
7.2 RabbitMQ
使用Erlang編寫的一個開源的消息隊列,本身支持很多的協議:AMQP,XMPP, SMTP,STOMP,也正是如此,使的它變的非常重量級,更適合於企業級的開發。同時實現了Broker架構,核心思想是生產者不會將消息直接發送給隊列,消息在發送給客戶端時先在中心隊列排隊。對路由(Routing),負載均衡(Load balance)、數據持久化都有很好的支持。多用於進行企業級的ESB整合。
7.3 ActiveMQ
Apache下的一個子項目。使用Java完全支持JMS1.1和J2EE 1.4規范的 JMS Provider實現,少量代碼就可以高效地實現高級應用場景。可插拔的傳輸協議支持,比如:in-VM, TCP, SSL, NIO, UDP, multicast, JGroups and JXTA transports。RabbitMQ、ZeroMQ、ActiveMQ均支持常用的多種語言客戶端 C++、Java、.Net,、python、 Php、 Ruby等。
7.4 Redis
使用C語言開發的一個Key-Value的NoSQL資料庫,開發維護很活躍,雖然它是一個Key-Value資料庫存儲系統,但它本身支持MQ功能,所以完全可以當做一個輕量級的隊列服務來使用。對於RabbitMQ和Redis的入隊和出隊操作,各執行100萬次,每10萬次記錄一次執行時間。測試數據分為128Bytes、512Bytes、1K和10K四個不同大小的數據。實驗表明:入隊時,當數據比較小時Redis的性能要高於RabbitMQ,而如果數據大小超過了10K,Redis則慢的無法忍受;出隊時,無論數據大小,Redis都表現出非常好的性能,而RabbitMQ的出隊性能則遠低於Redis。
7.5 Kafka
Apache下的一個子項目,使用scala實現的一個高性能分布式Publish/Subscribe消息隊列系統,具有以下特性:
7.6 ZeroMQ
號稱最快的消息隊列系統,專門為高吞吐量/低延遲的場景開發,在金融界的應用中經常使用,偏重於實時數據通信場景。ZMQ能夠實現RabbitMQ不擅長的高級/復雜的隊列,但是開發人員需要自己組合多種技術框架,開發成本高。因此ZeroMQ具有一個獨特的非中間件的模式,更像一個socket library,你不需要安裝和運行一個消息伺服器或中間件,因為你的應用程序本身就是使用ZeroMQ API完成邏輯服務的角色。但是ZeroMQ僅提供非持久性的隊列,如果down機,數據將會丟失。如:Twitter的Storm中使用ZeroMQ作為數據流的傳輸。
ZeroMQ套接字是與傳輸層無關的:ZeroMQ套接字對所有傳輸層協議定義了統一的API介面。默認支持 進程內(inproc) ,進程間(IPC) ,多播,TCP協議,在不同的協議之間切換只要簡單的改變連接字元串的前綴。可以在任何時候以最小的代價從進程間的本地通信切換到分布式下的TCP通信。ZeroMQ在背後處理連接建立,斷開和重連邏輯。
特性:
二、主要消息中間件的比較
② 為什麼大數據用python
Python 已經成為較受歡迎的程序設計語言之一。自從2004年以後,python的使用率呈線性增長。2011年1月,它被TIOBE編程語言排行榜評為2010年度語言。由於Python語言的簡潔性、易讀性以及可擴展性,在國外用Python做科學計算的研究機構日益增多,一些知名大學已經採用Python來教授程序設計課程。
數據就是資產。大數據工程師是現在十分火熱、高薪的職位。做大數據開發和分析不僅要用到Java,Python也是較重要的語言。
那麼,今天我們就來分析一下,Python之於大數據的意義和作用。
相關推薦:《Python入門教程》
什麼是大數據?
大數據(big data),指無法在一定時間范圍內用常規軟體工具進行捕捉、管理和處理的數據集合,是需要新處理模式才能具有更強的決策力、洞察發現力和流程優化能力的海量、高增長率和多樣化的信息資產。
為什麼是python大數據?
從大數據的網路介紹上看到,大數據想要成為信息資產,需要有兩步,一是數據怎麼來,二是數據處理。
數據怎麼來:
在數據怎麼來這個問題上,數據挖掘無疑是很多公司或者個人的優選,畢竟大部分公司或者個人是沒有能力產生這么多數據的,只能是挖掘互聯網上的相關數據。
網路爬蟲是Python的傳統強勢領域,較流行的爬蟲框架Scrapy,HTTP工具包urlib2,HTML解析工具beautifulsoup,XML解析器lxml,等等,都是能夠獨當一面的類庫。
當然,網路爬蟲並不僅僅只是打開網頁,解析HTML怎麼簡單。高效的爬蟲要能夠支持大量靈活的並發操作,常常要能夠同時幾千甚至上萬個網頁同時抓取,傳統的線程池方式資源浪費比較大,線程數上千之後系統資源基本上就全浪費在線程調度上了。
Python由於能夠很好的支持協程(Coroutine)操作,基於此發展起來很多並發庫,如Gevent,Eventlet,還有Celery之類的分布式任務框架。被認為是比AMQP更高效的ZeroMQ也是較早就提供了Python版本。有了對高並發的支持,網路爬蟲才真正可以達到大數據規模。
數據處理:
有了大數據,那麼也需要處理,才能找到適合自己的數據。而在數據處理方向,Python也是數據科學家較喜歡的語言之一,這是因為Python本身就是一門工程性語言,數據科學家用Python實現的演算法,可以直接用在產品中,這對於大數據初創公司節省成本是非常有幫助的。
正是因為這些原因,才讓python語言成為很多公司處理大數據的優選。加之python本身具有簡單、易學、庫多等原因,讓越來越多的人選擇轉行python開發。
③ 從 0 到 1:全面理解 RPC 遠程調用
作者 | Python編程時光
責編 | 胡巍巍
什麼是RPC呢?網路給出的解釋是這樣的:「RPC(Remote Procere Call Protocol)——遠程過程調用協議,它是一種通過網路從遠程計算機程序上請求服務,而不需要了解底層網路技術的協議」。
這個概念聽起來還是比較抽象,沒關系,繼續往後看,後面概念性的東西,我會講得足夠清楚,讓你完全掌握 RPC 的基礎內容。
在 OpenStack 里的進程間通信方式主要有兩種,一種是基於HTTP協議的RESTFul API方式,另一種則是RPC調用。
那麼這兩種方式在應用場景上有何區別呢?
有使用經驗的人,就會知道:
首先,給你提兩個問題,帶著這兩個問題再往下看:
1、RPC 和 REST 區別是什麼?2、為什麼要採用RPC呢?
首先,第一個問題:RPC 和 REST 區別是什麼?
你一定會覺得這個問題很奇怪,是的,包括我,但是你在網路上一搜,會發現類似對比的文章比比皆是,我在想可能很多初學者由於基礎不牢固,才會將不相乾的二者拿出來對比吧。既然是這樣,那為了讓你更加了解陌生的RPC,就從你熟悉得不能再熟悉的 REST 入手吧。
01、所屬類別不同
REST,是Representational State Transfer 的簡寫,中文描述表述性狀態傳遞(是指某個瞬間狀態的資源數據的快照,包括資源數據的內容、表述格式(XML、JSON)等信息。)
REST 是一種軟體架構風格。這種風格的典型應用,就是HTTP。其因為簡單、擴展性強的特點而廣頃肢受開發者的青睞。
而RPC 呢,是 Remote Procere Call Protocol 的簡寫,中文描述是遠程過程調用,它可以實現客戶端像調用本地服務(方法)一樣調用伺服器的服務(方法)。
而 RPC 可以基於 TCP/UDP,也可以基於 HTTP 協議進行傳輸的,按理說它和REST不是一個層面意義上的東西,不應該放在一起討論,但是誰讓REST這么流行呢,它是目前最流行的一套互聯網應用程序的API設計標准,某種意義下,我們說 REST 可以其實就是指代 HTTP 協議。
02、使用方式不同
03、面向對象不同
從設計上來看,RPC,所謂的遠程過程調用 ,是面向方法的 ,REST:所謂的 Representational state transfer ,是面向資源的,除此之外,還有一種叫做 SOA,所謂的面向服務的架構,它是面向消息的,這個接觸不多,就不多說了。
04、序列化協議不同
介面調用通常包含兩個部分,序列化和通信協議。
通信協議,上面已經提及了,REST 是 基於 HTTP 協議,而 RPC 可以基於 TCP/UDP,也可以基於 HTTP 協議進行傳輸的。
常見的序列化協議,有:json、xml、hession、protobuf、thrift、text、bytes等,REST 通常使用的是 JSON或者XML,而 RPC 使用的是渣歷 JSON-RPC,或者 XML-RPC。
通過以上幾點,我們知道了 REST 和 RPC 之間有很明顯的差異。
然後第二個問題:為什麼要採用RPC呢?
那到底為何要使用 RPC,單純的依靠RESTful API不可以嗎?為什麼要搞這么多復雜的協議,渣渣表示真的學不過來了。
關於這一點,以下幾點僅是我的個人猜想,僅供交流哈:
說了這么多,我們該如何選擇這兩者呢?我總結了如下兩點,供你參考:
「遠程調用」意思就是:被調用方法的具體實現不在程序運行本地,而是在別的某個地方(分布到各個伺服器),調用者只想要函數運算的結果,卻不需要實現函數的具體細節。
光說不練嘴把式,接下來,我將分別用三種不同的方式全面地讓你搞明白 rpc 遠程調用是如何實現的。
01、基於 xml-rpc
Python實現 rpc,可以使用標准庫里的 SimpleXMLRPCServer,它是基於XML-RPC 協議的。
有了這個模塊,開如乎搜啟一個 rpc server,就變得相當簡單了。執行以下代碼:
有了 rpc server,接下來就是 rpc client,由於我們上面使用的是 XML-RPC,所以 rpc clinet 需要使用xmlrpclib 這個庫。
然後,我們通過 server_proxy 對象就可以遠程調用之前的rpc server的函數了。
SimpleXMLRPCServer是一個單線程的伺服器。這意味著,如果幾個客戶端同時發出多個請求,其它的請求就必須等待第一個請求完成以後才能繼續。
若非要使用 SimpleXMLRPCServer 實現多線程並發,其實也不難。只要將代碼改成如下即可。
02、基於json-rpc
SimpleXMLRPCServer 是基於 xml-rpc 實現的遠程調用,上面我們也提到 除了 xml-rpc 之外,還有 json-rpc 協議。
那 python 如何實現基於 json-rpc 協議呢?
答案是很多,很多web框架其自身都自己實現了json-rpc,但我們要獨立這些框架之外,要尋求一種較為干凈的解決方案,我查找到的選擇有兩種
第一種是 jsonrpclib
第二種是 python-jsonrpc
先來看第一種 jsonrpclib
它與 Python 標准庫的 SimpleXMLRPCServer 很類似(因為它的類名就叫做 SimpleJSONRPCServer ,不明真相的人真以為它們是親兄弟)。或許可以說,jsonrpclib 就是仿照 SimpleXMLRPCServer 標准庫來進行編寫的。
它的導入與 SimpleXMLRPCServer 略有不同,因為SimpleJSONRPCServer分布在jsonrpclib庫中。
服務端
客戶端
再來看第二種python-jsonrpc,寫起來貌似有些復雜。
服務端
客戶端
調用過程如下
還記得上面我提到過的 zabbix API,因為我有接觸過,所以也拎出來講講。zabbix API 也是基於 json-rpc 2.0協議實現的。
因為內容較多,這里只帶大家打個,zabbix 是如何調用的:直接指明要調用 zabbix server 的哪個方法,要傳給這個方法的參數有哪些。
03、基於 zerorpc
以上介紹的兩種rpc遠程調用方式,如果你足夠細心,可以發現他們都是http+rpc 兩種協議結合實現的。
接下來,我們要介紹的這種(zerorpc),就不再使用走 http 了。
zerorpc 這個第三方庫,它是基於TCP協議、 ZeroMQ 和 MessagePack的,速度相對快,響應時間短,並發高。zerorpc 和 pyjsonrpc 一樣,需要額外安裝,雖然SimpleXMLRPCServer不需要額外安裝,但是SimpleXMLRPCServer性能相對差一些。
調用過程如下
客戶端除了可以使用zerorpc框架實現代碼調用之外,它還支持使用「命令行」的方式調用。
客戶端可以使用命令行,那服務端是不是也可以呢?
是的,通過 Github 上的文檔幾個 demo 可以體驗到這個第三方庫做真的是優秀。
比如我們可以用下面這個命令,創建一個rpc server,後面這個 time Python 標准庫中的 time 模塊,zerorpc 會將 time 注冊綁定以供client調用。
經過了上面的學習,我們已經學會了如何使用多種方式實現rpc遠程調用。
通過對比,zerorpc 可以說是脫穎而出,一支獨秀。
為此,我也做了一番思考:
OpenStack 組件繁多,在一個較大的集群內部每個組件內部通過rpc通信頻繁,如果都採用rpc直連調用的方式,連接數會非常地多,開銷大,若有些 server 是單線程的模式,超時會非常的嚴重。
OpenStack 是復雜的分布式集群架構,會有多個 rpc server 同時工作,假設有 server01,server02,server03 三個server,當 rpc client 要發出rpc請求時,發給哪個好呢?這是問題一。
你可能會說輪循或者隨機,這樣對大家都公平。這樣的話還會引出另一個問題,倘若請求剛好發到server01,而server01剛好不湊巧,可能由於機器或者其他因為導致服務沒在工作,那這個rpc消息可就直接失敗了呀。要知道做為一個集群,高可用是基本要求,如果出現剛剛那樣的情況其實是很尷尬的。這是問題二。
集群有可能根據實際需要擴充節點數量,如果使用直接調用,耦合度太高,不利於部署和生產。這是問題三。
引入消息中間件,可以很好的解決這些問題。
解決問題一:消息只有一份,接收者由AMQP的負載演算法決定,默認為在所有Receiver中均勻發送(round robin)。
解決問題二:有了消息中間件做緩沖站,client 可以任性隨意的發,server 都掛掉了?沒有關系,等 server 正常工作後,自己來消息中間件取就行了。
解決問題三:無論有多少節點,它們只要認識消息中間件這一個中介就足夠了。
既然講到了消息隊列,如果你之前沒有接觸過這塊內容,最好花幾分鍾的時間跟我好好過下關於消息隊列的幾個基礎概念。
首先,RPC只是定義了一個通信介面,其底層的實現可以各不相同,可以是 socket,也可以是今天要講的 AMQP。
AMQP(Advanced Message Queuing Protocol)是一種基於隊列的可靠消息服務協議,作為一種通信協議,AMQP同樣存在多個實現,如Apache Qpid,RabbitMQ等。
以下是 AMQP 中的幾個必知的概念:
Publisher:消息發布者
Queue:用來保存消息的存儲空間,消息沒有被receiver前,保存在隊列中。
Exchange:用來接收Publisher發出的消息,根據Routing key 轉發消息到對應的Message Queue中,至於轉到哪個隊列里,這個路由演算法又由exchange type決定的。
Exchange type:主要四種描述exchange的類型。
direct:消息路由到滿足此條件的隊列中(queue,可以有多個):routing key = binding key
topic:消息路由到滿足此條件的隊列中(queue,可以有多個):routing key 匹配 binding pattern. binding pattern是類似正則表達式的字元串,可以滿足復雜的路由條件。
fanout:消息路由到多有綁定到該exchange的隊列中。
binding :binding是用來描述exchange和queue之間的關系的概念,一個exchang可以綁定多個隊列,這些關系由binding建立。前面說的binding key /binding pattern也是在binding中給出。
為了讓你明白這幾者的關系,我畫了一張模型圖。
關於AMQP,有幾下幾點值得注意:
前面鋪墊了那麼久,終於到了講真實應用的場景。在生產中RPC是如何應用的呢?
其他模型我不太清楚,在 OpenStack 中的應用模型是這樣的
至於為什麼要如此設計,前面我已經給出了自己的觀點。
接下來,就是源碼解讀 OpenStack ,看看其是如何通過rpc進行遠程調用的。如若你對此沒有興趣(我知道很多人對此都沒有興趣,所以不浪費大家時間),可以直接跳過這一節,進入下一節。
目前Openstack中有兩種RPC實現,一種是在oslo messaging,一種是在openstack.common.rpc。
openstack.common.rpc是舊的實現,oslo messaging是對openstack.common.rpc的重構。openstack.common.rpc在每個項目中都存在一份拷貝,oslo messaging即將這些公共代碼抽取出來,形成一個新的項目。oslo messaging也對RPC API 進行了重新設計,對多種 transport 做了進一步封裝,底層也是用到了kombu這個AMQP庫。(註:Kombu 是Python中的messaging庫。Kombu旨在通過為AMQ協議提供慣用的高級介面,使Python中的消息傳遞盡可能簡單,並為常見的消息傳遞問題提供經過驗證和測試的解決方案。)
關於oslo_messaging庫,主要提供了兩種獨立的API:
因為 notify 實現是太簡單了,所以這里我就不多說了,如果有人想要看這方面內容,可以收藏我的博客(http://python-online.cn) ,我會更新補充 notify 的內容。
OpenStack RPC 模塊提供了 rpc.call,rpc.cast, rpc.fanout_cast 三種 RPC 調用方法,發送和接收 RPC 請求。
rpc.call 和 .rpc.cast 從實現代碼上看,他們的區別很小,就是call調用時候會帶有wait_for_reply=True參數,而cast不帶。
要了解 rpc 的調用機制呢,首先要知道 oslo_messaging 的幾個概念主要方法有四個:
transport:RPC功能的底層實現方法,這里是rabbitmq的消息隊列的訪問路徑
transport 就是定義你如何訪連接消息中間件,比如你使用的是 Rabbitmq,那在 nova.conf中應該有一行transport_url的配置,可以很清楚地看出指定了 rabbitmq 為消息中間件,並配置了連接rabbitmq的user,passwd,主機,埠。
target用來表述 RPC 伺服器監聽topic,server名稱和server監聽的exchange,是否廣播fanout。
rpc server 要獲取消息,需要定義target,就像一個門牌號一樣。
rpc client 要發送消息,也需要有target,說明消息要發到哪去。
endpoints:是可供別人遠程調用的對象
RPC伺服器暴露出endpoint,每個 endpoint 包涵一系列的可被遠程客戶端通過 transport 調用的方法。直觀理解,可以參考nova-conctor創建rpc server的代碼,這邊的endpoints就是 nova/manager.py:ConctorManager
dispatcher:分發器,這是 rpc server 才有的概念
只有通過它 server 端才知道接收到的rpc請求,要交給誰處理,怎麼處理?
在client端,是這樣指定要調用哪個方法的。
而在server端,是如何知道要執行這個方法的呢?這就是dispatcher 要乾的事,它從 endpoint 里找到這個方法,然後執行,最後返回。
Serializer:在 python 對象和message(notification) 之間數據做序列化或是反序列化的基類。
主要方法有四個:
每個notification listener都和一個executor綁定,來控制收到的notification如何分配。默認情況下,使用的是blocking executor(具體特性參加executor一節)
模仿是一種很高效的學習方法,我這里根據 OpenStack 的調用方式,抽取出核心內容,寫成一個簡單的 demo,有對 OpenStack 感興趣的可以了解一下,大部分人也可以直接跳過這章節。
注意以下代碼不能直接運行,你還需要配置 rabbitmq 的連接方式,你可以寫在配置文件中,通過 get_transport 從cfg.CONF 中讀取,也可以直接將其寫成url的格式做成參數,傳給 get_transport 。而且還要nova或者其他openstack組件的環境中運行(因為需要有ctxt這個環境變數)
簡單的 rpc client
簡單的 rpc server
【End】
熱 文 推 薦
☞Facebook 發幣 Libra;谷歌十億美金為窮人造房;第四代樹莓派 Raspberry Pi 4 發布 | 開發者周刊
☞WebRTC 將一統實時音視頻天下?
☞小米崔寶秋:小米 AIoT 深度擁抱開源
☞華為在美研發機構 Futurewei 意欲分家?
☞老司機教你如何寫出沒人敢維護的代碼!
☞Python有哪些技術上的優點?比其他語言好在哪兒?
☞上不了北大「圖靈」、清華「姚班」,AI專業還能去哪上?
☞公鏈史記 | 從鴻蒙初辟到萬物生長的十年激盪……
☞邊緣計算容器化是否有必要?
☞馬雲曾經偶像,終於把阿里留下的1400億敗光了!
你點的每個「在看」,我都認真當成了喜歡
④ 為什麼從事大數據行業,一定要學習Python
你好,這主要是因為Python在處理大數據方面有著得天獨厚的優勢。
以後您如果再遇到類似的問題,可以按照下面的思路去解決:
1、發現問題:往往生活在世界中,時時刻刻都處在這各種各樣的矛盾中,當某些矛盾放映到意識中時,個體才發現他是個問題,並要求設法去解決它。這就是發現問題的階段。從問題的解決的階段性看,這是第一階段,是解決問題的前提。
2、分析問題:要解決所發現的問題,必須明確問題的性質,也就是弄清楚有哪些矛盾、哪些矛盾方面,他們之間有什麼關系,以明確所要解決的問題要達到什麼結果,所必須具備的條件、其間的關系和已具有哪些條件,從而找出重要的矛盾、關鍵矛盾之所在。
3、提出假設:在分析問題的基礎上,提出解決問題的假設,即可採用的解決方案,其中包括採取什麼原則和具體的途徑和方法,但所有這些往往不是簡單現成的,而且有多種多樣的可能。但提出假設是問題解決的關鍵階段,正確的假設引導問題順利得到解決,不正確不恰當的假設則使問題的解決走彎路或導向歧途。
4、校驗假設:假設只是提出n種可能解決方案,還不能保證問題必定能獲得解決,所以問題解決的最後一步是對假設進行檢驗。不論哪種檢驗如果未能獲得預期結果,必須重新另提出假設再進行檢驗,直至獲得正確結果,問題才算解決。
⑤ OpenStack璇︾粏璧勬枡澶у叏
OpenStack鏄涓涓鐢盢ASA錛堢編鍥藉浗瀹惰埅絀鴻埅澶╁矓錛夊拰Rackspace鍚堜綔鐮斿彂騫跺彂璧風殑錛屼互Apache璁稿彲璇佹巿鏉冪殑鑷鐢辮蔣浣撳拰寮鏀懼師濮嬬爜欏圭洰銆
OpenStack鏄涓涓寮婧愮殑浜戣$畻綆$悊騫沖彴欏圭洰錛岀敱鍑犱釜涓昏佺殑緇勪歡緇勫悎璧鋒潵瀹屾垚鍏蜂綋宸ヤ綔銆侽penStack鏀鎸佸嚑涔庢墍鏈夌被鍨嬬殑浜戠幆澧冿紝欏圭洰鐩鏍囨槸鎻愪緵瀹炴柦綆鍗曘佸彲澶ц勬ā鎵╁睍銆佷赴瀵屻佹爣鍑嗙粺涓鐨勪簯璁$畻綆$悊騫沖彴銆侽penStack閫氳繃鍚勭嶄簰琛ョ殑鏈嶅姟鎻愪緵浜嗗熀紜璁炬柦鍗蟲湇鍔★紙IaaS錛夌殑瑙e喅鏂規堬紝姣忎釜鏈嶅姟鎻愪緵API浠ヨ繘琛岄泦鎴愩
OpenStack鏄涓涓鏃ㄥ湪涓哄叕鍏卞強縐佹湁浜戠殑寤鴻句笌綆$悊鎻愪緵杞浣撶殑寮婧愰」鐩銆傚畠鐨勭ぞ鍖烘嫢鏈夎秴榪130瀹朵紒涓氬強1350浣嶅紑鍙戣咃紝榪欎簺鏈烘瀯涓庝釜浜洪兘灝哋penStack浣滀負鍩虹璁炬柦鍗蟲湇鍔★紙IaaS錛夎祫婧愮殑閫氱敤鍓嶇銆侽penStack欏圭洰鐨勯栬佷換鍔℃槸綆鍖栦簯鐨勯儴緗茶繃紼嬪苟涓哄叾甯︽潵鑹濂界殑鍙鎵╁睍鎬с傛湰鏂囧笇鏈涢氳繃鎻愪緵蹇呰佺殑鎸囧間俊鎮錛屽府鍔╁ぇ瀹跺埄鐢∣penStack鍓嶇鏉ヨ懼畾鍙婄$悊鑷宸辯殑鍏鍏變簯鎴栫佹湁浜戙
OpenStack浜戣$畻騫沖彴錛屽府鍔╂湇鍔″晢鍜屼紒涓氬唴閮ㄥ疄鐜扮被浼間簬 Amazon EC2 鍜 S3 鐨勪簯鍩虹鏋舵瀯鏈嶅姟(Infrastructure as a Service, IaaS)銆侽penStack 鍖呭惈涓や釜涓昏佹ā緇勶細Nova 鍜 Swift錛屽墠鑰呮槸 NASA 寮鍙戠殑鉶氭嫙浼烘湇鍣ㄩ儴緗插拰涓氬姟璁$畻妯$粍錛涘悗鑰呮槸 Rackspace寮鍙戠殑鍒嗘暎寮忎簯瀛樺偍妯$粍錛屼袱鑰呭彲浠ヤ竴璧風敤錛屼篃鍙浠ュ垎寮鍗曠嫭鐢ㄣ侽penStack闄や簡鏈 Rackspace 鍜 NASA 鐨勫ぇ鍔涙敮鎸佸栵紝榪樻湁鍖呮嫭 Dell銆丆itrix銆 Cisco銆 Canonical絳夐噸閲忕駭鍏鍙哥殑璐$尞鍜屾敮鎸侊紝鍙戝睍閫熷害闈炲父蹇錛屾湁鍙栦唬鍙︿竴涓涓氱晫棰嗗厛寮婧愪簯騫沖彴 Eucalyptus 鐨勬佸娍銆
鍩烘湰浠嬬粛
- 涓鏂囧悕 錛歄penStack浜戣$畻綆$悊騫沖彴
- 澶栨枃鍚 錛歄penStack
- 寮鍙戣 錛歂ASA錛孯ackspace
- 紼嬪紡璇璦 錛歅ython
- 閬靛驚鏍囧噯 錛歄pen 銆丄MQP銆丼QLAlchemy
榪愮敤鑼冨洿
OpenStack鏄疘aaS(鍩虹璁炬柦鍗蟲湇鍔)緇勪歡錛岃╀換浣曚漢閮藉彲浠ヨ嚜琛屽緩絝嬪拰鎻愪緵 浜戠榪愮畻 鏈嶅姟銆 姝ゅ栵紝OpenStack涔熺敤浣滃緩絝 闃茬伀澧 鍐呯殑鈥 縐佹湁浜 鈥濓紙Private Cloud錛夛紝鎻愪緵鏈烘瀯鎴栦紒涓氬唴鍚勯儴闂ㄥ叡浜璧勬簮銆鍘傚晢鏀鎻
緹庡浗鍥藉惰埅絀鴻埅澶╁矓鐨凬ebula榪愮畻騫沖彴銆 緹庡浗鍥藉惰埅絀鴻埅澶╁矓鐨凬ebula榪愮畻騫沖彴銆 鐜版椂宸茶〃紺烘敮鎸丱penStack欏圭洰鐨勫ぇ鍨嬬‖浣撳巶鍟嗗寘鎷錛欼BM銆丄MD銆両ntel鍜屾埓灝旂瓑銆 寰杞鍦2010騫10鏈堣〃紺烘敮鎸丱penStack涓嶹indows Server 2008 R2鐨勬暣鍚堛 2011騫2鏈堬紝鎬濈戠郴緇熸e紡鍔犲叆OpenStack欏圭洰錛岄噸鐐圭爺鍒禣penStack鐨勭綉璺鏈嶅姟銆 Ubuntu鏈鏉ュ湪鍫嗗彔鏂歸潰鐨勪簯緗戣礬鍖栨柟妗堛 2012騫4鏈堬紝IBM瀹e竷鍔犲叆OpenStack欏圭洰錛屽苟浣滀負涓昏佽禐鍔╁晢銆 2012騫10鏈堬紝Viacloud浜掕仈浜戝鉤鍙板姞鍏OpenStack欏圭洰錛岀爺鍒禣penStack鍏鏈変簯騫沖彴鍜岀佹湁浜戝鉤鍙般 IBM鍦2013騫翠婦琛岀殑 IBM Pulse澶т細瀹e竷灝嗗熀浜嶰penStack鎻愪緵縐佹湁浜戞湇鍔′互鍙婄浉鍏沖楃敤銆鎶鏈璧勬枡
浠Python紼嬪紡璇璦緙栧啓 鏁村悎Tornado 緗戦〉浼烘湇鍣ㄣ丯ebula榪愮畻騫沖彴 浣跨敤Twisted杞浣撴嗘灦 閬靛驚Open Virtualization Format銆丄MQP銆丼QLAlchemy絳夋爣鍑 鉶氭嫙鏈哄櫒杞浣撴敮鎸佸寘鎷錛欿VM銆乆en銆乂irtualBox銆丵EMU銆 LXC 絳夈欏圭洰
鏍稿績欏圭洰
OpenStack瑕嗙洊浜嗙綉璺銆佽櫄鎷熷寲銆佷綔涓氱郴緇熴佷己鏈嶅櫒絳夊悇涓鏂歸潰銆傚畠鏄涓涓姝e湪寮鍙戜腑鐨勪簯璁$畻騫沖彴欏圭洰錛屾牴鎹鎴愮啛鍙婇噸瑕佺▼搴︾殑涓嶅悓錛岃鍒嗚В鎴愭牳蹇冮」鐩銆佸靛寲欏圭洰錛屼互鍙婃敮鎸侀」鐩鍜岀浉鍏抽」鐩銆傛瘡涓欏圭洰閮芥湁鑷宸辯殑濮斿憳浼氬拰欏圭洰鎶鏈涓葷★紝鑰屼笖姣忎釜欏圭洰閮戒笉鏄涓鎴愪笉鍙樼殑錛屽靛寲欏圭洰鍙浠ユ牴鎹鍙戝睍鐨勬垚鐔熷害鍜岄噸瑕佹э紝杞鍙樹負鏍稿績欏圭洰銆傛埅姝㈠埌Icehouse鐗堟湰錛屼笅闈㈠垪鍑轟簡10涓鏍稿績欏圭洰錛堝嵆OpenStack鏈嶅姟錛夈 璁$畻錛圕ompute錛夛細Nova銆備竴濂楁帶鍒跺櫒錛岀敤浜庝負鍗曚釜鐢ㄦ埛鎴栦嬌鐢ㄧ兢緇勭$悊鉶氭嫙鏈哄疄渚嬬殑鏁翠釜鐢熷懡鍛ㄦ湡錛屾牴鎹鐢ㄦ埛闇奼傛潵鎻愪緵鉶氭嫙鏈嶅姟銆傝礋璐h櫄鎷熸満鍒涘緩銆佸紑鏈恆佸叧鏈恆佹寕璧楓佹殏鍋溿佽皟鏁淬佽縼縐匯侀噸鍚銆侀攢姣佺瓑鎿嶄綔錛岄厤緗瓹PU銆佽板繂浣撶瓑淇℃伅瑙勬牸銆傝嚜Austin鐗堟湰闆嗘垚鍒伴」鐩涓銆 瀵硅薄瀛樺偍錛圤bject Storage錛夛細Swift銆備竴濂楃敤浜庡湪澶ц勬ā鍙鎵╁睍緋葷粺涓閫氳繃鍐呯疆鍐椾綑鍙婇珮瀹歸敊鏈哄埗瀹炵幇瀵硅薄瀛樺偍鐨勭郴緇燂紝鍏佽歌繘琛屽瓨鍌ㄦ垨鑰呮緔㈡。妗堛傚彲涓篏lance鎻愪緵闀滃儚瀛樺偍錛屼負Cinder鎻愪緵鍗峰囦喚鏈嶅姟銆傝嚜Austin鐗堟湰闆嗘垚鍒伴」鐩涓 闀滃儚鏈嶅姟錛圛mage Service錛夛細Glance銆備竴濂楄櫄鎷熸満闀滃儚鏌ユ壘鍙婃緔㈢郴緇燂紝鏀鎸佸氱嶈櫄鎷熸満闀滃儚鏍煎紡錛圓KI銆丄MI銆丄RI銆両SO銆丵COW2銆丷aw銆乂DI銆乂HD銆乂MDK錛夛紝鏈夊壋寤轟笂浼犻暅鍍忋佸垹闄ら暅鍍忋佺紪杈戦暅鍍忓熀鏈淇℃伅鐨勫姛鑳姐傝嚜Bexar鐗堟湰闆嗘垚鍒伴」鐩涓銆 韜浠芥湇鍔★紙Identity Service錛夛細Keystone銆備負OpenStack鍏朵粬鏈嶅姟鎻愪緵韜浠介獙璇併佹湇鍔¤勫垯鍜屾湇鍔′護鐗岀殑鍔熻兘錛岀$悊Domains銆丳rojects銆乁sers銆丟roups銆丷oles銆傝嚜Essex鐗堟湰闆嗘垚鍒伴」鐩涓銆 緗戣礬&鍦板潃綆$悊錛圢eork錛夛細Neutron銆傛彁渚涗簯璁$畻鐨勭綉璺鉶氭嫙鍖栨妧鏈錛屼負OpenStack鍏朵粬鏈嶅姟鎻愪緵緗戣礬榪炵嚎鏈嶅姟銆備負鐢ㄦ埛鎻愪緵鎺ュ彛錛屽彲浠ュ畾涔塏eork銆丼ub銆丷outer錛岄厤緗瓺HCP銆丏NS銆佽礋杞藉潎琛°丩3鏈嶅姟錛岀綉璺鏀鎸丟RE銆乂LAN銆傚栨寕紼嬪紡鏋舵瀯鏀鎸佽稿氫富嫻佺殑緗戣礬鍘傚跺拰鎶鏈錛屽侽penvSwitch銆傝嚜Folsom鐗堟湰闆嗘垚鍒伴」鐩涓銆 鍧楀瓨鍌 (Block Storage)錛欳inder銆備負榪愯屽疄渚嬫彁渚涚ǔ瀹氱殑鏁版嵁鍧楀瓨鍌ㄦ湇鍔★紝瀹冪殑澶栨寕紼嬪紡椹卞姩鏋舵瀯鏈夊埄浜庡潡璁懼囩殑鍒涘緩鍜岀$悊錛屽傚壋寤哄嵎銆佸垹闄ゅ嵎錛屽湪瀹炰緥涓婃寕杞藉拰鍗歌澆鍗楓傝嚜Folsom鐗堟湰闆嗘垚鍒伴」鐩涓銆 UI 鐣岄潰 (Dashboard)錛欻orizon銆侽penStack涓鍚勭嶆湇鍔$殑Web綆$悊闂ㄦ埛錛岀敤浜庣畝鍖栫敤鎴峰規湇鍔$殑鎿嶄綔錛屼緥濡傦細鍚鍔ㄥ疄渚嬨佸垎閰岻P浣嶅潃銆侀厤緗璁塊棶鎺у埗絳夈傝嚜Essex鐗堟湰闆嗘垚鍒伴」鐩涓銆 嫻嬮噺 (Metering)錛欳eilometer銆傚儚涓涓婕忔枟涓鏍鳳紝鑳芥妸OpenStack鍐呴儴鍙戠敓鐨勫嚑涔庢墍鏈夌殑浜嬩歡閮芥敹闆嗚搗鏉ワ紝鐒跺悗涓鴻¤垂鍜岀洃鎺т互鍙婂叾瀹冩湇鍔℃彁渚涙暟鎹鏀鎾戙傝嚜Havana鐗堟湰闆嗘垚鍒伴」鐩涓銆 閮ㄧ講緙栨帓 (Orchestration)錛欻eat銆傛彁渚涗簡涓縐嶉氳繃妯℃澘瀹氫箟鐨勫崗鍚岄儴緗叉柟寮忥紝瀹炵幇浜戝熀紜璁炬柦杞浣撹繍琛岀幆澧冿紙璁$畻銆佸瓨鍌ㄥ拰緗戣礬璧勬簮錛夌殑鑷鍔ㄥ寲閮ㄧ講銆傝嚜Havana鐗堟湰闆嗘垚鍒伴」鐩涓銆 璧勬枡搴撴湇鍔★紙Database Service錛夛細Trove銆備負鐢ㄦ埛鍦∣penStack鐨勭幆澧冩彁渚涘彲鎵╁睍鍜屽彲闈犵殑鍏崇郴鍜岄潪鍏崇郴璧勬枡搴撳紩鎿庢湇鍔°傝嚜Icehouse鐗堟湰闆嗘垚鍒伴」鐩涓銆紺懼尯欏圭洰
錛14涓錛 璐熻澆鍧囪錛欰tlas-LB錛圧ackspace錛 璁鎮浼鍒楋細Burrow錛圥iston錛 浜戠$悊宸ュ叿錛欳lanavi錛圖rupal錛 鑷鍔ㄩ儴緗詫細Crowbar錛圖ell錛 鏈嶅姟閮ㄧ講錛欽uju錛圲buntu錛 鍏崇郴鍨嬭祫鏂欏簱錛歊edDwarf錛圧ackspace錛 ...甯傚満瓚嬪悜
Rackspace浠OpenStack涓哄熀紜鐨勭佹湁浜戜笟鍔℃瘡騫磋惀鏀7浜跨編鍏冿紝澧為暱鐜囪秴榪囦簡20%銆 OpenStack鉶界劧鏈変簺鏂歸潰榪樹笉澶鎴愮啛錛岀劧鑰屽畠鏈夊叏鐞冨ぇ閲忕殑緇勭粐鏀鎸侊紝澶ч噺鐨勫紑鍙戜漢鍛樺弬涓庯紝鍙戝睍榪呴熴傚浗闄呬笂宸茬粡鏈夊緢澶氫嬌鐢∣penStack鎼寤虹殑鍏鏈変簯銆佺佹湁浜戙佹販鍚堜簯錛屼緥濡傦細RackspaceCloud銆佹儬鏅浜戙丮ercadoLibre鐨処T鍩虹璁炬柦浜戙丄T&T鐨凜loudArchitec銆佹埓灝旂殑OpenStack瑙e喅鏂規堢瓑絳夈傝屽湪鍥藉唴OpenStack鐨勭儹搴︿篃鍦ㄩ愭笎鍗囨俯錛屽崕鑳滃ぉ鎴愩侀珮寰峰湴鍥俱佷含涓溿侀樋閲屽反宸淬佺櫨搴︺佷腑鍏淬佸崕涓虹瓑閮藉筄penStack浜х敓浜嗘祿鍘氱殑鍏磋叮騫跺弬涓庡叾涓銆傝嚜2010騫村壋絝嬩互鏉ワ紝宸插彂甯10涓鐗堟湰銆傚叾涓璉cehouse鐗堟湰鏈120涓緇勭粐銆1202鍚嶄唬鐮佽礎鐚鑰呭弬涓庯紝鑰屾渶鏂扮殑鏄疛uno鐗堟湰銆侽penStack寰堝彲鑳藉湪鏈鏉ョ殑鍩虹璁炬柦鍗蟲湇鍔★紙IaaS錛夎祫婧愮$悊鏂歸潰鍗犳嵁棰嗗間綅緗錛屾垚涓哄叕鏈変簯銆佺佹湁浜戝強娣峰悎浜戠$悊鐨勨滀簯浣滀笟緋葷粺鈥濇爣鍑澶у瀷鐢ㄦ埛
緹庡浗鍥藉惰埅絀鴻埅澶╁矓 鍔犳嬁澶у崐瀹樻柟鏈烘瀯CANARIE緗戣礬鐨凞AIR錛圖igital Aelerator for Innovation and Research錛夐」鐩錛屽悜澶у︿笌涓灝忓瀷浼佷笟鎻愪緵鐮旂┒鍜屽紑鍙戜簯絝榪愮畻鐜澧冿紱DAIR鐢ㄦ埛鍙浠ユ寜闇瑕佸揩閫熷緩絝嬬綉璺鎷撴墤銆 鎯犳櫘浜戱紙浣跨敤Ubuntu Linux錛 MercadoLibre鐨処T鍩虹璁炬柦浜戱紝鐜版椂浠OpenStack綆$悊瓚呰繃6000 鍙拌櫄鎷熸満鍣ㄣ AT&T鐨勨淐loud Architect鈥濓紝灝嗗湪緹庡浗鐨勮揪鎷夋柉銆佸湥鍦頒簹鍝ュ拰鏂版辰瑗垮窞瀵瑰栨彁渚涗簯絝鏈嶅姟銆鍐呭硅﹁В
鍒涘緩鉶氭嫙鏈猴紙VM錛夐渶瑕佸悇縐嶆湇鍔$殑浜掑姩鍜岄厤鍚堝伐浣溿備笅鍥懼睍紺轟簡OpenStack鍏稿瀷鐜澧冩灦鏋勶紝鍚勪釜鏈嶅姟涔嬮棿鐨勪簰鍔ㄥ拰鑱岃兘銆 OpenStack鍏稿瀷鐜澧冩灦鏋 OpenStack鍥燨pen鑰屽紑鏀撅紝鍥犵粍浠惰岀伒媧伙紝鍥犲寘瀹硅屽崥澶с傛湁璁$畻銆佺綉璺銆佸硅薄瀛樺偍銆佸潡瀛樺偍銆佽韓浠姐侀暅鍍忔湇鍔°侀棬鎴楓佹祴閲忋侀儴緗茬紪鎺掋佽祫鏂欏簱鏈嶅姟絳夌瓑緇勪歡錛屾湁鐨勭粍浠跺彲浠ユ牴鎹闇瑕侀夋嫨瀹夎咃紝緇勭綉緇撴瀯涔熷緢鐏墊椿銆佸氭牱銆傚疄鐜頒簡鏀鎸佹帴鍏ュ氱嶄富嫻佽櫄鎷熸満杞浣擄細KVM銆丩XC銆丵EMU銆丠yper-V銆乂Mware銆乆enServer錛屼篃鍙浠ヨ嚜琛屽紑鍙戝栨寕紼嬪紡鎺ュ叆鍏朵粬鐨勮櫄鎷熷寲杞浣撱 OpenStack Compute (Nova)鏄涓濂楁帶鍒跺櫒錛岀敤浜庝負鍗曚釜鐢ㄦ埛鎴栦嬌鐢ㄧ兢緇勫惎鍔ㄨ櫄鎷熸満瀹炰緥銆傚畠鍚屾牱鑳藉熺敤浜庝負鍖呭惈鐫澶氫釜瀹炰緥鐨勭壒瀹氶」鐩璁懼畾緗戣礬銆侽penStack Compute鍦ㄥ叕鍏變簯澶勭悊鏂歸潰鍫涓嶢mazon EC2鐩告彁騫惰猴紱鑰屽湪縐佹湁浜戞柟闈涔熸涓嶉婅壊浜嶸Mware鐨勪駭鍝併傚湪鍏鍏變簯涓錛岃繖濂楃$悊鏈哄埗灝嗘彁渚涢勫埗鐨勯暅鍍忔垨鏄涓虹敤鎴峰壋寤虹殑闀滃儚鎻愪緵瀛樺偍鏈哄埗錛岃繖鏍風敤鎴峰氨鑳藉熷皢闀滃儚浠ヨ櫄鎷熸満鐨勫艦寮忓惎鍔ㄣ OpenStack 瀵硅薄瀛樺偍(Swift)鏄涓濂楃敤浜庡湪澶ц勬ā鍙鎵╁睍緋葷粺涓閫氳繃鍐呯疆鍐椾綑鍙婂歸敊鏈哄埗瀹炵幇瀵硅薄瀛樺偍鐨勭郴緇熴傝繖浜涘硅薄鑳藉熼氳繃涓涓猂EST API鎴栨槸鍍廋yberck榪欐牱鍙浠ュ規帴瀵硅薄瀛樺偍API鐨勫㈡埛絝鍔犱互鎮㈠嶃 OpenStack闀滃儚鏈嶅姟 (Glance)鏄涓濂楄櫄鎷熸満闀滃儚鏌ユ壘鍙婃緔㈢郴緇熴傚畠鑳藉熶互涓夌嶅艦寮忓姞浠ラ厤緗錛氬埄鐢∣penStack瀵硅薄瀛樺偍鏈哄埗鏉ュ瓨鍌ㄩ暅鍍忥紱鍒╃敤Amazon鐨勭畝鍗曞瓨鍌ㄨВ鍐蟲柟妗堬紙綆縐癝3錛夌洿鎺ュ瓨鍌ㄤ俊鎮錛涙垨鑰呭皢S3瀛樺偍涓庡硅薄瀛樺偍緇撳悎璧鋒潵錛屼綔涓篠3璁塊棶鐨勮繛綰垮櫒銆侽penStack闀滃儚鏈嶅姟鏀鎸佸氱嶈櫄鎷熸満闀滃儚鏍煎紡錛屽寘鎷琕Mware錛圴MDK錛夈丄mazon闀滃儚錛圓KI銆丄RI銆丄MI錛変互鍙奦irtualBox鎵鏀鎸佺殑鍚勭嶇佺熸牸寮忋傞暅鍍忓厓鏁版嵁鐨勫瑰櫒鏍煎紡鍖呮嫭Amazon鐨凙KI銆丄RI浠ュ強AMI淇℃伅錛屾爣鍑哋VF鏍煎紡浠ュ強浜岃繘鍒跺ぇ鍨嬫暟鎹銆 OpenStack鐨勫紑鍙戝懆鏈熸槸姣忓勾鍥哄畾鍙戝竷涓や釜鏂扮増鏈錛屽苟涓旀瘡涓涓鏂扮増杞浣撳彂甯冩椂錛屽紑鍙戣呬笌欏圭洰鎶鏈棰嗗艱呭凡緇忓湪瑙勫垝涓嬩竴涓鐗堟湰鐨勭粏鑺傘傝繖浜涘紑鍙戣呮潵鑷鍏ㄧ悆70澶氫釜緇勭粐錛岃秴榪1600浜恆備粬浠閲囩敤楂樼駭鐨勫伐鍏蜂笌寮鍙戞柟寮忥紝榪涜屼唬鐮佹煡鐪嬨佹寔緇鐨勯泦鎴愩佹祴璇曚笌寮鍙戞灦鏋勶紝璁╃増鏈鍦ㄥ揩閫熸垚闀跨殑鍚屾椂涔熻兘紜淇濈ǔ瀹氭с鏋勫緩縐佹湁浜
絎涓姝ユ槸璁懼畾姝g『鐨勭‖浣撳拰緗戣礬鐜澧冦傚敖綆OpenStack鍏佽稿湪涓涓鍗曚竴鐨勫鉤闈㈢綉璺涓婇儴緗蹭竴鍒囷紝浠庡畨鍏ㄧ殑瑙掑害鏉ョ湅騫朵笉瀹夊叏銆傚彇鍐充簬浣犳墍浣跨敤鐨勭$悊紼嬪紡浠ュ強鉶氭嫙緗戣礬鎺ュ彛錛屽畠浼氬厑璁竒uest鉶氭嫙鏈哄棶鎺㈢$悊嫻侀噺銆傚緩璁鑷沖皯浣跨敤涓や釜緗戣礬錛氫竴涓鐢ㄦ潵綆$悊嫻侀噺錛屼竴涓鐢ㄦ潵榪涜岃櫄鎷熸満涔嬮棿鐨勫硅瘽銆傝繖鎰忓懗鐫鎵鏈夌殑浜戣$畻緇撶偣涓浣犻渶瑕佷袱涓緗戝崱錛堜竴涓榪愯屽疄渚嬶級鍜岀綉璺綆$悊鑰呫傝繖浜涘簲璇ヨ繍琛屽湪涓嶅悓鐨処P鑼冨洿涓銆傝$畻緇撶偣鍜屽疄渚嬬殑緗戣礬涔熼渶瑕佹敮鎸乂LAN鏍囪幫紝鍥犱負榪欐槸鍦ㄢ滈」鐩鈥濅箣闂撮殧緇濇祦閲忔墍浣跨敤鐨勬満鍒躲備竴涓欏圭洰絳変環浜庝綘鐨勪簹椹閫奅C2璐︽埛錛岄櫎浜嗕綘涓嶈兘鎸夌収浣犳墍甯屾湜鐨勬暟鐩鍒涘緩鍜屽垎閰嶄箣澶栥傛瘡涓涓欏圭洰閮芥湁鑷宸辯殑綆$悊鍛樺拰鐢ㄦ埛錛屽湪鏃㈠畾欏圭洰涓鐨勬墍鏈夊疄渚嬪彲浠ュ郊姝ら氫俊銆傞氳繃鎸囨淳姣忎竴涓欏圭洰鑷宸辯殑VLAN浠ュ強鍐呴儴鍜屽栭儴鐨処P浣嶅潃奼犳潵鎵ц屻 涓鏃︾‖浣撳拰緗戣礬璁懼畾濂斤紝涓嬩竴姝ュ氨鏄紜瀹氬湪鍝閲岄儴緗叉墍鏈夌殑OpenStack緇勪歡銆傛爣鍑嗛儴緗插簲鏈変竴涓鎺у埗鍣ㄥ拰涓緋誨垪璁$畻緇撶偣銆傛帶鍒跺櫒榪愯岃鎮浼烘湇鍣錛岃祫鏂欏簱鍜屽叾浠栫殑緇勪歡鏉ョ紪鎺掍簯錛屽悓鏃惰$畻緇撶偣榪愯屽疄渚嬨備絾鏄浣犱篃鍙浠ュ垎瑙f帶鍒跺櫒涓哄湴鐞嗙殑閮ㄥ垎錛屼粠鑰屾敼鍠勬ц兘錛屽儚鎶奙ySQL鏀懼湪涓嶅悓鐨勭墿鐞嗙洅涓銆傚逛簬瀹夊叏鑰岃█錛屾渶鍏抽敭鐨勬槸紜淇濇瘡涓閮ㄥ垎閮藉畨瑁呭湪瀹夊叏鐨勪富鏈轟笂錛屼綘鍙闇瑕佸皢鍏墮檮鍔犲湪緗戣礬涓婏紝璁╀簯榪愯漿鍗沖彲銆 鍙鏈変袱閮ㄥ垎闇瑕佹毚闇茬粰澶栭潰鐨勪笘鐣岋紙鍗充嬌閭e彧鏄浣犵殑浼佷笟緗戣礬錛夛細API浼烘湇鍣/Web 鎺у埗鍙幫紙濡傛灉寮鍚錛夊拰緗戣礬綆$悊鑰呫傝繖浜涗己鏈嶅櫒闇瑕佽繃紜錛屼綘鐢氳嚦鍙浠ヤ嬌鐢ㄧ涓夋柟緗戣礬鎺ュ彛鏉ラ殧紱誨悗絝綆$悊鐢ㄦ埛榪炵嚎浜х敓鐨勬祦閲忋 濡傛灉浣犻伒寰榛樿ゅ畨瑁呰存槑涔︼紝鍙鑳借繖浜涢儴鍒嗗苟涓嶅備粬浠搴旇ョ殑閭f牱瀹夊叏銆備笅闈㈡槸涓浜涘叿浣撶殑鏀瑰彉錛 * MySQL浼烘湇鍣ㄤ嬌鐢ㄦ寚瀹氱殑鐢ㄦ埛璐︽埛錛屼笉鏄鏍筂ySQL綆$悊璐︽埛銆傝繖涓璐︽埛鍜屽瘑鐮佸皢浼氭毚闇插湪姣忎竴涓浜戠粨鐐逛笂錛屽嵆浣誇嬌鐢ㄥ熀浜庤瘉涔︾殑璁よ瘉錛屽洜姝ゆ墍鏈夌粨鐐歸渶瑕佽塊棶榪欎釜璧勬枡搴撲己鏈嶅櫒銆 * MySQL閰嶇疆妗f堜腑錛岄檺鍒惰塊棶浼烘湇鍣錛孫penStack鐢ㄦ埛璐︽埛涓哄敮涓鎺堟潈IP浣嶅潃銆 * 縐婚櫎浠諱綍涓嶉渶瑕佺殑OS緇勪歡騫剁『淇濅綘鎵璁懼畾鐨勪己鏈嶅櫒鍙鏀鎸侀氳繃SSH鐨勫熀浜庡瘑閽ョ殑鐧誨叆銆 * 榛樿MySQL鍜孯abbitMQ錛堣鎮浼烘湇鍣錛夋祦閲忎笉鍔犲瘑銆傚傛灉浣犻殧紱諱簡綆$悊緗戣礬鍜屽潥鍥虹殑涓繪満錛岃繖灝變笉搴旇ユ槸涓涓寰堢碂緋曠殑椋庨櫓銆傚傛灉浣犵殑浜戠綉璺鏄撲簬鍡呮帰錛堜緥濡傦紝瀹冨拰鍏朵粬浼烘湇鍣ㄥ叡浜緗戣礬錛夛紝浣犻渶瑕佸姞瀵嗘祦閲忋備綘鍙浠ヤ嬌鐢∣penSSL鏉ヨ繘琛孧ySQL 鍜孯abbitMQ澶勭悊銆傦紙鎴戜釜浜鴻繕娌¤繘琛屾祴璇曪紝鍥犳ら厤緗鍙鑳芥湁鐐歸毦銆傦級 涓嬩竴姝ワ紝璁頒綇濡傛灉鏀鎸乄eb綆$悊鎺у埗鍙幫紝榛樿や笉閫傜敤SSL銆鏈嶅姟涓蹇
涓鍥絆penStack鏈嶅姟涓蹇姒傝堪
2013騫6鏈18鏃ュ湪鍗椾含鍙寮浜嗏滀腑鍥戒簯璁$畻浜т笟淇冭繘澶т細鏆ㄤ腑鍥絆penStack鏈嶅姟涓蹇冨彂甯冧細鈥濓紝鍗庤儨澶╂垚鍦ㄤ細涓婃e紡瀹e竷鎺ㄥ嚭涓鍥介栧禣penStack鏈嶅姟涓蹇冦侽penStack鏄鍏ㄧ悆寮鍙戣呭叡鍚屽弬涓庣殑涓涓寮婧愰」鐩錛屾棬鍦ㄥ疄鐜扳滀簯浣滀笟緋葷粺鈥濓紝鍗充竴涓鍏鋒湁閮ㄧ講鍜岀$悊鍏鏈変簯銆佺佹湁浜戜互鍙婃販鍚堜簯鍩虹鏋舵瀯鑳藉姏鐨勫鉤鍙般 1銆佸緩璁懼苟榪愯惀涓鍥界涓涔熷彲鑳芥槸鍞涓鐨凮penstack鏀鎸佷腑蹇冦 2銆佷負Openstack鐨勭爺絀惰咃紝寮鍙戣呭拰浣跨敤鑰呮彁渚涗赴瀵岀殑綰誇笂鍙婄幇鍦轟笓涓氭敮鎸佹湇鍔″拰鍜ㄨ㈡湇鍔★紝娑堥櫎瀹㈡埛浣跨敤寮婧愯蔣浣撶殑鍚庨【涔嬪咖銆 3銆佹彁楂樺浗鍐呬簯璁$畻浠庝笟浜哄憳鏁伴噺鍜岀礌璐錛屾櫘鍙婂紑婧愯蔣浣撶簿紲炰笌鎶鏈銆 4銆佹墦鐮翠簯璁$畻寤鴻劇殑鍨勬柇錛屽ぇ澶ч檷浣庝簯璁$畻騫沖彴寤鴻句笌榪愯惀鎴愭湰錛屾帹鍔ㄥ苟淇濋殰鍥藉唴浜戣$畻騫沖彴寤鴻捐摤鍕冨彂灞曘緋葷粺鏋勬垚
800鐢佃瘽鏀鎸佷腑蹇冿紙100鍧愬腑錛 Web綰誇笂鏀鎸佸鉤鍙幫紙100鍧愬腑錛 鏈嶅姟鐢靛瓙閿鍞騫沖彴 鐭ヨ瘑搴 CRM緋葷粺 涓撲笟鍜ㄨ㈠洟闃燂紙10浜猴級 涓撲笟鐜板満鎶鏈鏀鎸佸洟闃燂紙50浜猴級 涓撲笟瀹㈡埛鍖栧紑鍙戝洟闃燂紙100浜猴級 涓撲笟榪愮淮綆$悊鍥㈤槦錛300浜猴級 鍏ㄧ悆瀹為獙瀹ょ駭鏀鎸佸洟闃燂紙2涓鍥介檯欏剁駭鏍稿績浠g爜瀹為獙瀹わ級鏈嶅姟鍐呭
鎻愪緵瀹屽杽鐨凩1錛孡2浠ュ強L3瀹為獙瀹ょ駭鍒綰誇笂涓庣幇鍦烘湇鍔 24*7鐢佃瘽鍜ㄨ/鏀鎸佹湇鍔★紝Web綰誇笂鍜ㄨ㈡湇鍔/鏀鎸佹湇鍔 鐗堟湰鍙戝竷涓庡崌綰ф湇鍔 嫻嬭瘯鏈嶅姟 鐜板満瀹夎咃紝鍗囩駭/璋冧紭鏈嶅姟 瀹氬埗寮鍙戞湇鍔 鍩硅鏈嶅姟 鐭ヨ瘑搴撳叡浜鏈嶅姟 榪愮淮鏈嶅姟 鐢靛瓙浜ゆ槗鏈嶅姟浣撻獙
1銆佸㈡埛鍙浠24灝忔椂閫氳繃鐢佃瘽鎴栫綉璺鍦ㄦ敮鎸佷腑蹇冭幏寰楀府鍔╋紝鍖呮嫭浜戞妧鏈鍜ㄨ錛岃祫鏂欑儲鍙栵紝璐涔版湇鍔″寘銆 2銆佹敹璐規湇鍔″寘鍒嗕負綰у埆錛堜緥錛 鍩烘湰鏈嶅姟鍖咃紙5*8 鐢佃瘽鏀鎸佹湇鍔★級 鏍囧噯鏈嶅姟鍖咃紙7*24鐢佃瘽鏀鎸佹湇鍔+鐜板満鏈嶅姟錛 楂樼駭鏈嶅姟鍖咃紙7*24*6騫沖彴淇澶嶄繚璇侊級 3銆佷笓涓氭湇鍔¢夐」錛堜緥錛 緋葷粺闆嗘垚鏈嶅姟 涓撲漢鍊煎畧鏈嶅姟 緋葷粺璋冧紭鏈嶅姟 緋葷粺榪佺Щ鏈嶅姟 宸℃鏈嶅姟 榪愮淮綆$悊鏈嶅姟 搴旀ュ洖鍝嶆湇鍔 鍩硅鏈嶅姟鏈嶅姟浠峰
1銆佸瑰紑婧愪簯璁$畻鐨勭敤鎴峰拰娼滃湪鐢ㄦ埛 鎻愪緵浜嗕竴涓鑾峰緱鐭ヨ瘑錛屾寚瀵煎拰鎶鏈鏀鎸佺殑娓犻亾錛岃В鍐充簡濂楃敤寮婧愪簯鎶鏈鎵句笉鍒版妧鏈鍚庣浘鐨勫按灝灞闈銆 鎻愪緵浜嗕竴涓楂樻按騫崇殑鎶鏈鍥㈤槦瀵圭敤鎴瘋繘琛屽畨瑁咃紝閰嶇疆錛屽紑鍙戱紝鏈浣沖寲錛岃繍緇存湇鍔★紝浣誇簯璁$畻騫沖彴鍙浠ユg『鐨勮閮ㄧ講鍜屼嬌鐢錛岀湡姝d駭鐢熸晥鐩娿 2銆佸逛簬Openstack浜т笟閾 淇冭繘Openstack鍦ㄤ腑鍥界殑钀藉湴鐢熸牴錛屽紑鑺辯粨鏋溿傝В鍐充簡Openstack闆鵑噷鐪嬭姳鐨勫按灝銆 3銆佸逛簬鏀鎸佷腑蹇冩湰韜 鑾峰緱澶ч噺鐨勫㈡埛淇℃伅鍜岄」鐩鏈轟細錛岃幏寰楅珮鍒╂鼎鐨勬湇鍔′笟鍔°傝仛鍚堝ぇ閲忎笟鍐呮妧鏈璧勬簮錛屽艦鎴愭妧鏈璧勬簮奼狅紝騫墮氳繃鑱氬悎鏁堝簲浣誇駭涓氶摼鍏卞悓鎴愰暱銆 4銆佸圭ぞ浼 澶уぇ淇冭繘浜戝緩璁炬ヤ紣錛岄檷浣嶪T榪愯惀鎴愭湰錛屾彁楂樹笟鍔℃晱鎹峰害錛岃妭鑳藉噺鎺掞紝淇冭繘浜т笟鍗囩駭銆鎴愬憳浼佷笟
鍗庤儨澶╂垚 Intel Canonical Rackspace 涓鍥藉紑婧愪簯鑱旂洘
⑥ 消息隊列原理及選型
消息隊列(Message Queue)是一種進程間通信或同一進程的不同線程間的通信方式。
Broker(消息伺服器)
Broker的概念來自與Apache ActiveMQ,通俗的講就是MQ的伺服器。
Procer(生產者)
業務的發起方,負責生產消息傳輸給broker
Consumer(消費者)
業務的處理方,負責從broker獲取消息並進行業務邏輯處理
Topic(主題)
發布訂閱模式下的消息統一匯集地,不同生產者向topic發送消息,由MQ伺服器分發到不同的訂閱 者,實現消息的廣播
Queue(隊列)
PTP模式下,特定生產者向特定queue發送消息,消費者訂閱特定的queue完成指定消息的接收。
Message(消息體)
根據不同通信協議定義的固定格式進行編碼的數據包,來封裝業務數據,實現消息的傳輸
點對點模型用於消息生產者和消息消費者之間點到點的通信。
點對點模式包含三個角色:
每個消息都被發送到一個特定的隊列,接收者從隊列中獲取消息。隊列保留著消息,可以放在內存 中也可以持久化,直到他們被消費或超時。
特點:
發布訂閱模型包含三個角色:
多個發布者將消息發送到Topic,系統將這些消息傳遞給多個訂閱者。
特點:
AMQP即Advanced Message Queuing Protocol,是應用層協議的一個開放標准,為面向消息的中間件設計。消息中間件主要用於組件之間的解耦,消息的發送者無需知道消息使用者的存在,反之亦然。AMQP 的主要特徵是面向消息、隊列、路由(包括點對點和發布/訂閱)、可靠性、安全。
優點:可靠、通用
MQTT(Message Queuing Telemetry Transport,消息隊列遙測傳輸)是IBM開發的一個即時通訊協議,有可能成為物聯網的重要組成部分。該協議支持所有平台,幾乎可以把所有聯網物品和外部連接起來,被用來當做感測器和致動器(比如通過Twitter讓房屋聯網)的通信協議。
優點:格式簡潔、佔用帶寬小、移動端通信、PUSH、嵌入式系統
STOMP(Streaming Text Orientated Message Protocol)是流文本定向消息協議,是一種為MOM(Message Oriented Middleware,面向消息的中間件)設計的簡單文本協議。STOMP提供一個可互操作的連接格式,允許客戶端與任意STOMP消息代理(Broker)進行交互。
優點:命令模式(非topicqueue模式)
XMPP(可擴展消息處理現場協議,Extensible Messaging and Presence Protocol)是基於可擴展標記語言(XML)的協議,多用於即時消息(IM)以及在線現場探測。適用於伺服器之間的准即時操作。核心是基於XML流傳輸,這個協議可能最終允許網際網路用戶向網際網路上的其他任何人發送即時消息,即使其操作系統和瀏覽器不同。
優點:通用公開、兼容性強、可擴展、安全性高,但XML編碼格式佔用帶寬大
RabbitMQ 是實現 AMQP(高級消息隊列協議)的消息中間件的一種,最初起源於金融系統,用於在分布式系統中存儲轉發消息,在易用性、擴展性、高可用性等方面表現不俗。 RabbitMQ 主要是為了實現系統之間的雙向解耦而實現的。當生產者大量產生數據時,消費者無法快速消費,那麼需要一個中間層。保存這個數據。
RabbitMQ 是一個開源的 AMQP 實現,伺服器端用Erlang語言編寫,支持多種客戶端,如:Python、Ruby、.NET、Java、JMS、C、PHP、ActionScript、XMPP、STOMP 等,支持 AJAX。用於在分布式系統中存儲轉發消息,在易用性、擴展性、高可用性等方面表現不俗。
Channel(通道)
道是兩個管理器之間的一種單向點對點的的通信連接,如果需要雙向交流,可以建立一對通道。
Exchange(消息交換機)
Exchange類似於數據通信網路中的交換機,提供消息路由策略。
RabbitMq中,procer不是通過信道直接將消息發送給queue,而是先發送給Exchange。一個Exchange可以和多個Queue進行綁定,procer在傳遞消息的時候,會傳遞一個ROUTING_KEY,Exchange會根據這個ROUTING_KEY按照特定的路由演算法,將消息路由給指定的queue。和Queue一樣,Exchange也可設置為持久化,臨時或者自動刪除。
Exchange有4種類型:direct(默認),fanout, topic, 和headers。
不同類型的Exchange轉發消息的策略有所區別:
Binding(綁定)
所謂綁定就是將一個特定的 Exchange 和一個特定的 Queue 綁定起來。Exchange 和Queue的綁定可以是多對多的關系。
Routing Key(路由關鍵字)
exchange根據這個關鍵字進行消息投遞。
vhost(虛擬主機)
在RabbitMq server上可以創建多個虛擬的message broker,又叫做virtual hosts (vhosts)。每一個vhost本質上是一個mini-rabbitmq server,分別管理各自的exchange,和bindings。vhost相當於物理的server,可以為不同app提供邊界隔離,使得應用安全的運行在不同的vhost實例上,相互之間不會干擾。procer和consumer連接rabbit server需要指定一個vhost。
假設P1和C1注冊了相同的Broker,Exchange和Queue。P1發送的消息最終會被C1消費。
基本的通信流程大概如下所示:
Consumer收到消息時需要顯式的向rabbit broker發送basic。ack消息或者consumer訂閱消息時設置auto_ack參數為true。
在通信過程中,隊列對ACK的處理有以下幾種情況:
即消息的Ackownledge確認機制,為了保證消息不丟失,消息隊列提供了消息Acknowledge機制,即ACK機制,當Consumer確認消息已經被消費處理,發送一個ACK給消息隊列,此時消息隊列便可以刪除這個消息了。如果Consumer宕機/關閉,沒有發送ACK,消息隊列將認為這個消息沒有被處理,會將這個消息重新發送給其他的Consumer重新消費處理。
消息的收發處理支持事務,例如:在任務中心場景中,一次處理可能涉及多個消息的接收、處理,這應該處於同一個事務范圍內,如果一個消息處理失敗,事務回滾,消息重新回到隊列中。
消息的持久化,對於一些關鍵的核心業務來說是非常重要的,啟用消息持久化後,消息隊列宕機重啟後,消息可以從持久化存儲恢復,消息不丟失,可以繼續消費處理。
fanout 模式
模式特點:
direct 模式
任何發送到Direct Exchange的消息都會被轉發到routing_key中指定的Queue。
如果一個exchange 聲明為direct,並且bind中指定了routing_key,那麼發送消息時需要同時指明該exchange和routing_key。
簡而言之就是:生產者生成消息發送給Exchange, Exchange根據Exchange類型和basic_publish中的routing_key進行消息發送 消費者:訂閱Exchange並根據Exchange類型和binding key(bindings 中的routing key) ,如果生產者和訂閱者的routing_key相同,Exchange就會路由到那個隊列。
topic 模式
前面講到direct類型的Exchange路由規則是完全匹配binding key與routing key,但這種嚴格的匹配方式在很多情況下不能滿足實際業務需求。
topic類型的Exchange在匹配規則上進行了擴展,它與direct類型的Exchage相似,也是將消息路由到binding key與routing key相匹配的Queue中,但這里的匹配規則有些不同。
它約定:
以上圖中的配置為例,routingKey=」quick.orange.rabbit」的消息會同時路由到Q1與Q2,routingKey=」lazy.orange.fox」的消息會路由到Q1,routingKey=」lazy.brown.fox」的消息會路由到Q2,routingKey=」lazy.pink.rabbit」的消息會路由到Q2(只會投遞給Q2一次,雖然這個routingKey與Q2的兩個bindingKey都匹配);routingKey=」quick.brown.fox」、routingKey=」orange」、routingKey=」quick.orange.male.rabbit」的消息將會被丟棄,因為它們沒有匹配任何bindingKey。
RabbitMQ,部署分三種模式:單機模式,普通集群模式,鏡像集群模式。
普通集群模式
多台機器部署,每個機器放一個rabbitmq實例,但是創建的queue只會放在一個rabbitmq實例上,每個實例同步queue的元數據。
如果消費時連的是其他實例,那個實例會從queue所在實例拉取數據。這就會導致拉取數據的開銷,如果那個放queue的實例宕機了,那麼其他實例就無法從那個實例拉取,即便開啟了消息持久化,讓rabbitmq落地存儲消息的話,消息不一定會丟,但得等這個實例恢復了,然後才可以繼續從這個queue拉取數據, 這就沒什麼高可用可言,主要是提供吞吐量 ,讓集群中多個節點來服務某個queue的讀寫操作。
鏡像集群模式
queue的元數據和消息都會存放在多個實例,每次寫消息就自動同步到多個queue實例里。這樣任何一個機器宕機,其他機器都可以頂上,但是性能開銷太大,消息同步導致網路帶寬壓力和消耗很重,另外,沒有擴展性可言,如果queue負載很重,加機器,新增的機器也包含了這個queue的所有數據,並沒有辦法線性擴展你的queue。此時,需要開啟鏡像集群模式,在rabbitmq管理控制台新增一個策略,將數據同步到指定數量的節點,然後你再次創建queue的時候,應用這個策略,就會自動將數據同步到其他的節點上去了。
Kafka 是 Apache 的子項目,是一個高性能跨語言的分布式發布/訂閱消息隊列系統(沒有嚴格實現 JMS 規范的點對點模型,但可以實現其效果),在企業開發中有廣泛的應用。高性能是其最大優勢,劣勢是消息的可靠性(丟失或重復),這個劣勢是為了換取高性能,開發者可以以稍降低性能,來換取消息的可靠性。
一個Topic可以認為是一類消息,每個topic將被分成多個partition(區),每個partition在存儲層面是append log文件。任何發布到此partition的消息都會被直接追加到log文件的尾部,每條消息在文件中的位置稱為offset(偏移量),offset為一個long型數字,它是唯一標記一條消息。它唯一的標記一條消息。kafka並沒有提供其他額外的索引機制來存儲offset,因為在kafka中幾乎不允許對消息進行「隨機讀寫」。
Kafka和JMS(Java Message Service)實現(activeMQ)不同的是:即使消息被消費,消息仍然不會被立即刪除。日誌文件將會根據broker中的配置要求,保留一定的時間之後刪除;比如log文件保留2天,那麼兩天後,文件會被清除,無論其中的消息是否被消費。kafka通過這種簡單的手段,來釋放磁碟空間,以及減少消息消費之後對文件內容改動的磁碟IO開支。
對於consumer而言,它需要保存消費消息的offset,對於offset的保存和使用,有consumer來控制;當consumer正常消費消息時,offset將會"線性"的向前驅動,即消息將依次順序被消費。事實上consumer可以使用任意順序消費消息,它只需要將offset重置為任意值。(offset將會保存在zookeeper中,參見下文)
kafka集群幾乎不需要維護任何consumer和procer狀態信息,這些信息有zookeeper保存;因此procer和consumer的客戶端實現非常輕量級,它們可以隨意離開,而不會對集群造成額外的影響。
partitions的設計目的有多個。最根本原因是kafka基於文件存儲。通過分區,可以將日誌內容分散到多個server上,來避免文件尺寸達到單機磁碟的上限,每個partiton都會被當前server(kafka實例)保存;可以將一個topic切分多任意多個partitions,來消息保存/消費的效率。此外越多的partitions意味著可以容納更多的consumer,有效提升並發消費的能力。(具體原理參見下文)。
一個Topic的多個partitions,被分布在kafka集群中的多個server上;每個server(kafka實例)負責partitions中消息的讀寫操作;此外kafka還可以配置partitions需要備份的個數(replicas),每個partition將會被備份到多台機器上,以提高可用性。
基於replicated方案,那麼就意味著需要對多個備份進行調度;每個partition都有一個server為"leader";leader負責所有的讀寫操作,如果leader失效,那麼將會有其他follower來接管(成為新的leader);follower只是單調的和leader跟進,同步消息即可。由此可見作為leader的server承載了全部的請求壓力,因此從集群的整體考慮,有多少個partitions就意味著有多少個"leader",kafka會將"leader"均衡的分散在每個實例上,來確保整體的性能穩定。
Procers
Procer將消息發布到指定的Topic中,同時Procer也能決定將此消息歸屬於哪個partition;比如基於"round-robin"方式或者通過其他的一些演算法等。
Consumers
本質上kafka只支持Topic。每個consumer屬於一個consumer group;反過來說,每個group中可以有多個consumer。發送到Topic的消息,只會被訂閱此Topic的每個group中的一個consumer消費。
如果所有的consumer都具有相同的group,這種情況和queue模式很像;消息將會在consumers之間負載均衡。
如果所有的consumer都具有不同的group,那這就是"發布-訂閱";消息將會廣播給所有的消費者。
在kafka中,一個partition中的消息只會被group中的一個consumer消費;每個group中consumer消息消費互相獨立;我們可以認為一個group是一個"訂閱"者,一個Topic中的每個partions,只會被一個"訂閱者"中的一個consumer消費,不過一個consumer可以消費多個partitions中的消息。kafka只能保證一個partition中的消息被某個consumer消費時,消息是順序的。事實上,從Topic角度來說,消息仍不是有序的。
Kafka的設計原理決定,對於一個topic,同一個group中不能有多於partitions個數的consumer同時消費,否則將意味著某些consumer將無法得到消息。
Guarantees
Kafka就比較適合高吞吐量並且允許少量數據丟失的場景,如果非要保證「消息可靠傳輸」,可以使用JMS。
Kafka Procer 消息發送有兩種方式(配置參數 procer.type):
對於同步方式(procer.type=sync)?Kafka Procer 消息發送有三種確認方式(配置參數 acks):
kafka的設計初衷是希望作為一個統一的信息收集平台,能夠實時的收集反饋信息,並需要能夠支撐較大的數據量,且具備良好的容錯能力。
持久性
kafka使用文件存儲消息,這就直接決定kafka在性能上嚴重依賴文件系統的本身特性。且無論任何OS下,對文件系統本身的優化幾乎沒有可能。文件緩存/直接內存映射等是常用的手段。因為kafka是對日誌文件進行append操作,因此磁碟檢索的開支是較小的;同時為了減少磁碟寫入的次數,broker會將消息暫時buffer起來,當消息的個數(或尺寸)達到一定閥值時,再flush到磁碟,這樣減少了磁碟IO調用的次數。
性能
需要考慮的影響性能點很多,除磁碟IO之外,我們還需要考慮網路IO,這直接關繫到kafka的吞吐量問題。kafka並沒有提供太多高超的技巧;對於procer端,可以將消息buffer起來,當消息的條數達到一定閥值時,批量發送給broker;對於consumer端也是一樣,批量fetch多條消息。不過消息量的大小可以通過配置文件來指定。對於kafka broker端,似乎有個sendfile系統調用可以潛在的提升網路IO的性能:將文件的數據映射到系統內存中,socket直接讀取相應的內存區域即可,而無需進程再次和交換。 其實對於procer/consumer/broker三者而言,CPU的開支應該都不大,因此啟用消息壓縮機制是一個良好的策略;壓縮需要消耗少量的CPU資源,不過對於kafka而言,網路IO更應該需要考慮。可以將任何在網路上傳輸的消息都經過壓縮。kafka支持gzip/snappy等多種壓縮方式。
生產者
負載均衡: procer將會和Topic下所有partition leader保持socket連接;消息由procer直接通過socket發送到broker,中間不會經過任何「路由層「。事實上,消息被路由到哪個partition上,有procer客戶端決定。比如可以採用「random「「key-hash「「輪詢「等,如果一個topic中有多個partitions,那麼在procer端實現「消息均衡分發「是必要的。
其中partition leader的位置(host:port)注冊在zookeeper中,procer作為zookeeper client,已經注冊了watch用來監聽partition leader的變更事件。
非同步發送:將多條消息暫且在客戶端buffer起來,並將他們批量的發送到broker,小數據IO太多,會拖慢整體的網路延遲,批量延遲發送事實上提升了網路效率。不過這也有一定的隱患,比如說當procer失效時,那些尚未發送的消息將會丟失。
消費者
consumer端向broker發送「fetch」請求,並告知其獲取消息的offset;此後consumer將會獲得一定條數的消息;consumer端也可以重置offset來重新消費消息。
在JMS實現中,Topic模型基於push方式,即broker將消息推送給consumer端。不過在kafka中,採用了pull方式,即consumer在和broker建立連接之後,主動去pull(或者說fetch)消息;這中模式有些優點,首先consumer端可以根據自己的消費能力適時的去fetch消息並處理,且可以控制消息消費的進度(offset);此外,消費者可以良好的控制消息消費的數量,batch fetch。
其他JMS實現,消息消費的位置是有prodiver保留,以便避免重復發送消息或者將沒有消費成功的消息重發等,同時還要控制消息的狀態。這就要求JMS broker需要太多額外的工作。在kafka中,partition中的消息只有一個consumer在消費,且不存在消息狀態的控制,也沒有復雜的消息確認機制,可見kafka broker端是相當輕量級的。當消息被consumer接收之後,consumer可以在本地保存最後消息的offset,並間歇性的向zookeeper注冊offset。由此可見,consumer客戶端也很輕量級。
對於JMS實現,消息傳輸擔保非常直接:有且只有一次(exactly once)。
在kafka中稍有不同:
at most once: 消費者fetch消息,然後保存offset,然後處理消息;當client保存offset之後,但是在消息處理過程中出現了異常,導致部分消息未能繼續處理。那麼此後"未處理"的消息將不能被fetch到,這就是"at most once"。
at least once: 消費者fetch消息,然後處理消息,然後保存offset。如果消息處理成功之後,但是在保存offset階段zookeeper異常導致保存操作未能執行成功,這就導致接下來再次fetch時可能獲得上次已經處理過的消息,這就是"at least once",原因offset沒有及時的提交給zookeeper,zookeeper恢復正常還是之前offset狀態。
exactly once: kafka中並沒有嚴格的去實現(基於2階段提交,事務),我們認為這種策略在kafka中是沒有必要的。
通常情況下「at-least-once」是我們首選。(相比at most once而言,重復接收數據總比丟失數據要好)。
kafka高可用由多個broker組成,每個broker是一個節點;
創建一個topic,這個topic會劃分為多個partition,每個partition存在於不同的broker上,每個partition就放一部分數據。
kafka是一個分布式消息隊列,就是說一個topic的數據,是分散放在不同的機器上,每個機器就放一部分數據。
在0.8版本以前,是沒有HA機制的,就是任何一個broker宕機了,那個broker上的partition就廢了,沒法寫也沒法讀,沒有什麼高可用性可言。
0.8版本以後,才提供了HA機制,也就是就是replica副本機制。每個partition的數據都會同步到其他的機器上,形成自己的多個replica副本。然後所有replica會選舉一個leader出來,那麼生產和消費都跟這個leader打交道,然後其他replica就是follower。
寫的時候,leader會負責把數據同步到所有follower上去,讀的時候就直接讀leader上數據即可。
kafka會均勻的將一個partition的所有replica分布在不同的機器上,從而提高容錯性。
如果某個broker宕機了也沒事,它上面的partition在其他機器上都有副本的,如果這上面有某個partition的leader,那麼此時會重新選舉一個新的leader出來,大家繼續讀寫那個新的leader即可。這就有所謂的高可用性了。
寫數據的時候,生產者就寫leader,然後leader將數據落地寫本地磁碟,接著其他follower自己主動從leader來pull數據。一旦所有follower同步好數據了,就會發送ack給leader,leader收到所有follower的ack之後,就會返回寫成功的消息給生產者。
消息丟失會出現在三個環節,分別是生產者、mq中間件、消費者:
RabbitMQ
Kafka
大體和RabbitMQ相同。
Rabbitmq
需要保證順序的消息投遞到同一個queue中,這個queue只能有一個consumer,如果需要提升性能,可以用內存隊列做排隊,然後分發給底層不同的worker來處理。
Kafka
寫入一個partition中的數據一定是有序的。生產者在寫的時候 ,可以指定一個key,比如指定訂單id作為key,這個訂單相關數據一定會被分發到一個partition中去。消費者從partition中取出數據的時候也一定是有序的,把每個數據放入對應的一個內存隊列,一個partition中有幾條相關數據就用幾個內存隊列,消費者開啟多個線程,每個線程處理一個內存隊列。
⑦ openstack用的python什麼框架
openstack是最近3年學習python的人最值得學習的一個雲計算框架。
OpenStack 包含兩個主要模塊:Nova 和 Swift,前者是 NASA 開發的虛擬伺服器部署和業務計算模塊;後者是 Rackspace開發的分布式雲存儲模塊,兩者可以一起用,也可以分開單獨用。
在ubuntu操作系統上,可以很輕松安裝openstack這個私有雲框架。而openstack就是用Python編程語言編寫的。
整合Tornado 網頁伺服器(快速響應)、Nebula運算平台
使用Twisted軟體框架(高並發)
遵循Open Virtualization Format、AMQP、SQLAlchemy等標准
虛擬機器軟體支持包括:KVM、Xen、VirtualBox、QEMU、 LXC 等。
KVM相對速度要快些。xen比較新。virtualbox是以qemu為基礎做的談慧。LXC還沒有用過大槐。
python如果不喜歡,想做openstack也沒有問題,畢竟它只是一個框架含仿答與語言本身相差很大的。
比如你不喜歡java,但不等於你不會在android上開發APP。這與JAVA語言本身關系不大。