接口調(diào)度者——API 網(wǎng)關(guān)

image
image

背景

我們知道在微服務(wù)架構(gòu)風(fēng)格中,一個大應(yīng)用被拆分成為了多個小的服務(wù)系統(tǒng)提供出來瞄勾,這些小的服務(wù)他們自成體系塘揣,也就是說這些小系統(tǒng)可以擁有自己的數(shù)據(jù)庫,框架甚至語言等憋他,這些小系統(tǒng)通常以提供 Rest Api 風(fēng)格的接口來被 H5, Android, IOS 以及第三方應(yīng)用程序調(diào)用孩饼。
在《淺入淺出消息隊列》這一篇文章中,我提到了消息隊列是方便服務(wù)與服務(wù)之間的通信解耦竹挡,如下圖所示:

image.png
image.png

那么這時候問題來了镀娶,如果一個外部的應(yīng)用(瀏覽器、App)要去訪問這個大應(yīng)用怎么辦揪罕?
很簡單啊梯码,直接通過HTTP請求不就完了?

問題

真的這么簡單嗎好啰?我們以淘寶的商品詳情頁為例:


image
image

如上圖所示轩娶,這個頁面包含了視頻、庫存框往、商品價格鳄抒、商品評價等內(nèi)容,這些數(shù)據(jù)都來自不同的微服務(wù)中椰弊,所以沒辦法像傳統(tǒng)單體應(yīng)用一樣依靠數(shù)據(jù)庫的 join 查詢來得到最終結(jié)果许溅,因此就需要多次調(diào)用以檢索數(shù)據(jù),如下圖所示:


image.png
image.png

這就會引發(fā)幾個嚴重的問題:
  • 不同的客戶端設(shè)備可能需要不同的數(shù)據(jù)秉版。Web,H5,APP贤重,需要單獨寫一套API
  • 多次客戶端請求導(dǎo)致用戶體驗不佳。移動網(wǎng)絡(luò)相較于服務(wù)于服務(wù)間的局域網(wǎng)沐飘,有更低的帶寬和更高的延時游桩,如果可以同時執(zhí)行請求倒也還好,但如果客戶端要按照順序執(zhí)行請求耐朴,就會讓用戶體驗變得異常糟糕借卧。
  • 缺乏封裝導(dǎo)致前后端不協(xié)調(diào)。過分的拆分API筛峭,會導(dǎo)致客戶端和服務(wù)端過度耦合铐刘,再加上移動端APP的新版本迭代到每個手機用戶時需要很久,這樣會使后端很難更改服務(wù)的API影晓。

這樣顯然是不好的設(shè)計镰吵,因此檩禾,本期的“天降猛男”就出現(xiàn)了——API網(wǎng)關(guān)。

API網(wǎng)關(guān)

再介紹API網(wǎng)關(guān)前疤祭,我們先來介紹一個設(shè)計模式——外觀模式盼产。
外觀模式(Facade Pattern)它向現(xiàn)有的系統(tǒng)添加一個接口,來隱藏系統(tǒng)的復(fù)雜性勺馆。類圖如下所示:

image
image

之所以要在說API網(wǎng)關(guān)前說一下外觀模式戏售,是因為二者的設(shè)計理念是類似的。

和外觀模式類似草穆,API 網(wǎng)關(guān)封裝了應(yīng)用程序的內(nèi)部架構(gòu)灌灾,并為其客戶端提供API,他還可能具有其他職責(zé)悲柱,如身份驗證锋喜、監(jiān)控、負載均衡豌鸡、緩存嘿般、請求分片與管理、靜態(tài)響應(yīng)處理直颅。下圖展示了客戶端博个、API網(wǎng)關(guān)和服務(wù)之間的關(guān)系。

image
image

所有的客戶端和消費端都通過統(tǒng)一的網(wǎng)關(guān)接入微服務(wù)功偿,在網(wǎng)關(guān)層處理所有的非業(yè)務(wù)功能。其出現(xiàn)也是側(cè)面貫徹了軟件工程中"高內(nèi)聚往堡,低耦合"的思想械荷。

核心作用

API 網(wǎng)關(guān)負責(zé)請求路由、API組合和協(xié)議轉(zhuǎn)換虑灰。來自外部客戶端的所有API請求首先會先轉(zhuǎn)到API網(wǎng)關(guān)吨瞎,后者再將請求路由到相應(yīng)的服務(wù)。API網(wǎng)關(guān)使用API組合模式處理其他請求穆咐,調(diào)用多個服務(wù)并聚合結(jié)果颤诀。同時他還可以在客戶端友好的協(xié)議(例如HTTP)與客戶端不友好的協(xié)議之間進行轉(zhuǎn)換。

請求路由

當(dāng)API網(wǎng)關(guān)收到請求時对湃,隨機會查詢路由映射崖叫,該映射將指定請求路由到哪個服務(wù)。例如拍柒,路由映射可以將HTTP方法和路徑映射到服務(wù)的HTTP URL心傀,這一點和Nginx提供的反向代理的功能是一樣的,后面我們也會對其進行一個比較拆讯。
既然有路由映射脂男,那存放在哪就是一個問題了养叛,我們需要為API網(wǎng)關(guān)設(shè)置一個路由映射的存儲位置,通過可能會用zookeeper等作為注冊中心來使用宰翅,文末我們也會提一下弊端挠进。

API組合

除去反向代理這個功能外,API網(wǎng)關(guān)還提供了API組合的操作帘靡。以上面的淘寶詳情頁為例乐严,如果我們單獨獲取視頻、商品價格掉缺、商品評論等信息卜录,需要發(fā)多個請求(getVideo,getPrice,getComments)。有了API網(wǎng)關(guān)后我們就可以將API接口組合起來眶明,通過一次請求(getItemDetail)來獲取需要的信息艰毒,如下圖所示,這樣可以極大的改善由于網(wǎng)絡(luò)延時導(dǎo)致的差用戶體驗搜囱。


image
image

協(xié)議轉(zhuǎn)換

API網(wǎng)關(guān)可以為外部客戶端提供RESTful API丑瞧,即使內(nèi)部的服務(wù)使用混合的通信協(xié)議,例如REST蜀肘、gRPC等绊汹。這樣做的好處是,對于外部客戶端而言扮宠,服務(wù)端更像是一個不可見的黑盒西乖。

API網(wǎng)關(guān)和Nginx

本質(zhì)上看API網(wǎng)關(guān)也是做了請求的轉(zhuǎn)發(fā),那既然Nginx也可以做請求轉(zhuǎn)發(fā)坛增,這兩者有什么區(qū)別获雕?
一張圖就可以很好的理解了。

image
image

Nginx做負載均衡時收捣,考慮到API網(wǎng)關(guān)在系統(tǒng)中不止一個(以集群的方式做高可用)届案,我們可以將Nginx至于API網(wǎng)關(guān)前,負責(zé)對API網(wǎng)關(guān)的負載均衡罢艾,然后再由網(wǎng)關(guān)決定進入到哪個真實的web 服務(wù)器楣颠。
這樣就可以讓兩者的分工更加明確:API網(wǎng)關(guān)聚合服務(wù),Nginx請求轉(zhuǎn)發(fā)

API 網(wǎng)關(guān)的優(yōu)缺點

API網(wǎng)關(guān)封裝了應(yīng)用程序的內(nèi)部結(jié)構(gòu)咐蚯,使得客戶端只需要同網(wǎng)關(guān)交互童漩,而不必調(diào)用特定的服務(wù)。同時API 網(wǎng)關(guān)為每一類客戶端提供了特定的 API 仓蛆,從而減少客戶端與應(yīng)用程序間的交互次數(shù)睁冬,簡化客戶端代碼的處理。
但就和所有中間件一樣,他們都存在一個共同的問題豆拨,API網(wǎng)關(guān)的存在使系統(tǒng)增加了一個必須開發(fā)直奋、部署和維護的高可用組件。如果這個組件沒有處理好施禾,那么 API 網(wǎng)關(guān)就會變成了應(yīng)用的性能瓶頸脚线。
而且為了暴露每個微服務(wù),開發(fā)人員必須更新 API 網(wǎng)關(guān)弥搞,所以就有可能會搭配其他服務(wù)發(fā)現(xiàn)類的中間件使用邮绿,例如zookeeper,這樣就又引入了新的中間件攀例。所以我們需要保證API 網(wǎng)關(guān)的更新過程要盡可能地簡單船逮,否則為了更新網(wǎng)關(guān),開發(fā)人員將不得不排隊等待粤铭。
由此可見挖胃,API網(wǎng)關(guān)也并不是一顆"銀彈",我們在中間件的選擇上還是需要結(jié)合項目的實際情況梆惯,萬不可追求新穎就濫用中間件酱鸭,適合自己的才是最好的。不過垛吗,API網(wǎng)關(guān)雖然仍有不足凹髓,但對于大多數(shù)現(xiàn)實世界的應(yīng)用程序而言使用 API 網(wǎng)關(guān)是合理的。

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末怯屉,一起剝皮案震驚了整個濱河市蔚舀,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌蚀之,老刑警劉巖蝗敢,帶你破解...
    沈念sama閱讀 221,576評論 6 515
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異足删,居然都是意外死亡,警方通過查閱死者的電腦和手機锁右,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 94,515評論 3 399
  • 文/潘曉璐 我一進店門失受,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人咏瑟,你說我怎么就攤上這事拂到。” “怎么了码泞?”我有些...
    開封第一講書人閱讀 168,017評論 0 360
  • 文/不壞的土叔 我叫張陵兄旬,是天一觀的道長。 經(jīng)常有香客問我,道長领铐,這世上最難降的妖魔是什么悯森? 我笑而不...
    開封第一講書人閱讀 59,626評論 1 296
  • 正文 為了忘掉前任,我火速辦了婚禮绪撵,結(jié)果婚禮上瓢姻,老公的妹妹穿的比我還像新娘。我一直安慰自己音诈,他們只是感情好幻碱,可當(dāng)我...
    茶點故事閱讀 68,625評論 6 397
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著细溅,像睡著了一般褥傍。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上喇聊,一...
    開封第一講書人閱讀 52,255評論 1 308
  • 那天恍风,我揣著相機與錄音,去河邊找鬼承疲。 笑死邻耕,一個胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的燕鸽。 我是一名探鬼主播兄世,決...
    沈念sama閱讀 40,825評論 3 421
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼啊研!你這毒婦竟也來了御滩?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 39,729評論 0 276
  • 序言:老撾萬榮一對情侶失蹤党远,失蹤者是張志新(化名)和其女友劉穎削解,沒想到半個月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體沟娱,經(jīng)...
    沈念sama閱讀 46,271評論 1 320
  • 正文 獨居荒郊野嶺守林人離奇死亡氛驮,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 38,363評論 3 340
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了济似。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片矫废。...
    茶點故事閱讀 40,498評論 1 352
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖砰蠢,靈堂內(nèi)的尸體忽然破棺而出蓖扑,到底是詐尸還是另有隱情,我是刑警寧澤台舱,帶...
    沈念sama閱讀 36,183評論 5 350
  • 正文 年R本政府宣布律杠,位于F島的核電站,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏柜去。R本人自食惡果不足惜灰嫉,卻給世界環(huán)境...
    茶點故事閱讀 41,867評論 3 333
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望诡蜓。 院中可真熱鬧熬甫,春花似錦、人聲如沸蔓罚。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,338評論 0 24
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽豺谈。三九已至郑象,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間茬末,已是汗流浹背厂榛。 一陣腳步聲響...
    開封第一講書人閱讀 33,458評論 1 272
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留丽惭,地道東北人击奶。 一個月前我還...
    沈念sama閱讀 48,906評論 3 376
  • 正文 我出身青樓,卻偏偏與公主長得像责掏,于是被迫代替她去往敵國和親柜砾。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點故事閱讀 45,507評論 2 359