成人免费xxxxx在线视频软件_久久精品久久久_亚洲国产精品久久久_天天色天天色_亚洲人成一区_欧美一级欧美三级在线观看

從 ListWatch 到 WatchList

云計(jì)算 云原生
新版中已經(jīng)修復(fù)了 List Stale Read 的問(wèn)題,對(duì)于前兩種情況,其會(huì)先從 kube-apiserver 獲取 Etcd 最新的 RV,等待 WatchCache Store 內(nèi)容追平 RV 后再一次性的返回。

分析

可以先設(shè)想一下如果自己去實(shí)現(xiàn)的話,該如何設(shè)計(jì)。Client 和 Server 端都要去適配這是必然的,因?yàn)?Informer 現(xiàn)在是 ListWatch 機(jī)制,服務(wù)端并不支持流式 List。因此可以有個(gè)初步的方向:

  1. Server 端支持流式 List 請(qǐng)求
  2. Informer 適配 Server 端 API 的變化

客戶端的適配相對(duì)簡(jiǎn)單,重點(diǎn)還是放在 Server 端如何實(shí)現(xiàn)。先回顧下之前 List 的邏輯,在前一篇 Stale Read 里面已經(jīng)介紹過(guò)了。

為方面描述,下文統(tǒng)一使用 RV 代指 Resourceversion,本節(jié)邏輯均基于 v1.26.9 版本,且忽略分頁(yè)查詢,因?yàn)榉猪?yè)是直接走 Etcd 的。

無(wú)論是 List 還是 Watch 請(qǐng)求,其 query 均支持傳入 RV,服務(wù)端會(huì)根據(jù)請(qǐng)求的 RV 的不同做相應(yīng)的處理,根據(jù) RV 的值可以分為三種情況

  1. 未設(shè)置或者顯示設(shè)置 RV=""
  2. RV = "0"
  3. RV = "非 0 值"

對(duì)于前兩種情況,List 會(huì)直接返回 WatchCache Store 中的內(nèi)容,即服務(wù)端緩存好的 Etcd 的全部相關(guān)數(shù)據(jù)。

對(duì)于第三種情況,會(huì)等待服務(wù)端緩存數(shù)據(jù)的最大版本要超過(guò)傳入的 RV 之后再返回緩存內(nèi)的數(shù)據(jù),如果等待了一段時(shí)間(3s)后緩存中的數(shù)據(jù)仍然沒(méi)有達(dá)到指定版本,則會(huì)報(bào)錯(cuò)返回 "Too large resource version",并告訴客戶端可以在 1s 之后重試。

新版中已經(jīng)修復(fù)了 List Stale Read 的問(wèn)題,對(duì)于前兩種情況,其會(huì)先從 kube-apiserver 獲取 Etcd 最新的 RV,等待 WatchCache Store 內(nèi)容追平 RV 后再一次性的返回。

也就是說(shuō)服務(wù)端是可以知道自己是否已經(jīng)包含最新全量數(shù)據(jù)的,在這個(gè)基礎(chǔ)上再以流式方式返回即可。當(dāng)前已有的流式 API 就是 Watch,所以可以在此基礎(chǔ)上支持 List 的效果。為什么不直接在 List 請(qǐng)求基礎(chǔ)上改呢,因?yàn)楦?List 的話,會(huì)涉及到太多的客戶端側(cè)的適配,List 會(huì)經(jīng)常單獨(dú)使用,而 Watch 基本是在 Informer 里面使用。

所以最終的工作就會(huì)變成如何使用 Watch API 實(shí)現(xiàn) List 的效果,但數(shù)據(jù)仍然以流式返回給客戶端,同時(shí) Informer 修改 ListWatch 方式為只使用 Watch API 實(shí)現(xiàn)之前的效果。下文以詳細(xì)介紹服務(wù)端實(shí)現(xiàn)為主,客戶端適配的部分會(huì)比較簡(jiǎn)單的介紹下。

原理

通過(guò)為 Watch API 添加一個(gè) SendInitialEvents=true 參數(shù)來(lái)支持 List 的效果。Server 端接收到 Watch 請(qǐng)求后判斷哪些數(shù)據(jù)是應(yīng)該作為 InitEvents 發(fā)送給客戶端,同時(shí)在發(fā)送完這些數(shù)據(jù)之后發(fā)送一個(gè)特定的 BOOKMARK Event(帶特定 Annotation 的 BOOKMARK,其 RV 對(duì)應(yīng)下文的 bookmarkAfterRV)給客戶端作為服務(wù)端通知客戶端 InitEvents 發(fā)送完畢的標(biāo)志,客戶端在接收到指定 BOOKMARK Event 后,將之前接收到的所有 InitEvent 作為 List 的結(jié)果處理。

時(shí)序圖

下面是基于 v1.29 代碼的分析,此時(shí) v1.29 還在 alpha 狀態(tài),提到的舊版代表 1.27 之前的版本,新版代表 v1.29。如果你看到的代碼和下面描述的不一致,有可能是代碼版本導(dǎo)致的。

圖片圖片

從 WatchCache 開(kāi)始右面四個(gè)藍(lán)色的是在 kube-apiserver 啟動(dòng)的時(shí)候開(kāi)始執(zhí)行的,G1 G2 代表兩個(gè) goroutine,分別用來(lái)從 Etcd 獲取數(shù)據(jù),以及發(fā)送數(shù)據(jù)給客戶端 CacheWatcher 的 input chan

  1. G1.1 每種資源類型對(duì)應(yīng)一個(gè) Cacher,內(nèi)部包含一個(gè) Reflector,WatchCache 作為 Reflector 的 Store 存儲(chǔ)從 Etcd 獲取到的數(shù)據(jù);
  2. G1.2 Reflector 開(kāi)啟調(diào)用 Etcd List 和 Watch API 獲取數(shù)據(jù);
  3. G1.3 Reflector 利用獲取到的數(shù)據(jù)更新 WatchCache 的 store 和 cyclic buffer,兩者分別用來(lái)存儲(chǔ)全量的對(duì)象和對(duì)象的最近更新事件;
  4. G1.4 在更新完 WatchCache 后,會(huì)把 Event 發(fā)送到 Cacher 的 incoming chan 中;
  5. G2.1 從 Cacher 的 imcomming chan 中消費(fèi)數(shù)據(jù)發(fā)送給所有的 CacheWatcher 的 input chan,或者定時(shí)(1 ~ 1.25s)發(fā)送 RV > bookmarkAfterRV 的 BOOKMARK 事件給所有的 CacheWatcher 的 input chan;

上述過(guò)程描述了服務(wù)端啟動(dòng)時(shí)的數(shù)據(jù)處理流程,接下來(lái)看有客戶端請(qǐng)求時(shí)的處理流程

  1. Reflector 首次發(fā)起 Watch 請(qǐng)求,query 中指定 RV=""&sendInitialEvent=true&resourceVersinotallow=NotOlderThan&AllowWatchBookmarks=true,這里無(wú)論 RV="" 還是 RV="0" 都可以實(shí)現(xiàn) List 的效果,只不過(guò)相比舊版本的實(shí)現(xiàn),新版里面 Watch 請(qǐng)求針對(duì) RV="" 做了特殊處理,解決了 Watch API Stale Read 的問(wèn)題(List Stale Read 已經(jīng)在前一篇中介紹過(guò)了,針對(duì) List 提供了 FeatureGate 來(lái)控制是否開(kāi)啟 Consistent Read,但 Watch 這里并沒(méi)有對(duì)應(yīng)的 FeatureGate,也即是說(shuō)新版中針對(duì) RV="" 的請(qǐng)求一定是 Consistent Read),服務(wù)端接收到請(qǐng)求后為這個(gè)請(qǐng)求創(chuàng)建對(duì)應(yīng)的 CacheWachter 對(duì)象;
  2. Server 端在接收到請(qǐng)求后計(jì)算 bookmarkAfterRV 的值,如果 RV="0",則 bookmarkAfterRV 就是 WatchCache RV(WatchCache Store 數(shù)據(jù)中的最大 RV),如果 RV="",則去 Etcd 中獲取最大的 RV 作為 bookmarkAfterRV,將 bookmarkAfterRV 傳遞給 CacheWatcher,最后 CacheWatcher 會(huì)結(jié)合 WatchCache Store 和自身 input chan 中的數(shù)據(jù)準(zhǔn)備 InitEvents

2a 開(kāi)始從 WatchCache Store 中獲取需要返回的數(shù)據(jù),此時(shí)的處理邏輯舊版本相同,返回 Store 中的全部數(shù)據(jù),并記錄 Store 數(shù)據(jù)的最大 RV 供下一步使用;

2b 消費(fèi) input chan 中的事件,對(duì)比其 RV 是否比 2a 傳入的 RV 大,或者如果是 BOOKMARK 類型并且 RV 等與 2a 傳入的 RV,且尚未發(fā)送 bookmarkAfterRV 的事件,則此 BOOKMARK 事件就會(huì)被當(dāng)做 List 結(jié)束的標(biāo)志,為其設(shè)置 Annotation: k8s.io/initial-events-end,最后發(fā)送給客戶端;

至此,服務(wù)端的主要流程已經(jīng)介紹完,客戶端 Informer 也做了對(duì)應(yīng)的適配,如果開(kāi)啟 WathList 功能的話,會(huì)發(fā)送 Watch 請(qǐng)求來(lái)獲取一遍全量數(shù)據(jù),等到接收到攜帶 Annotation: k8s.io/initial-events-end 的 BOOKMARK 事件后,記錄其 RV,將在此期間接受并處理后的對(duì)象作為 List 的結(jié)果。最后再次以上述 RV 作為參數(shù)調(diào)用 Watch 請(qǐng)求,從這一步開(kāi)始就是 Informer 傳統(tǒng)意義上的 Watch 邏輯了。

數(shù)據(jù)流

圖片圖片

圖片來(lái)自 KEP 3157 watch-list,其實(shí)里面也包含時(shí)序圖,不過(guò)里面的書(shū)序圖畫(huà)的有一些問(wèn)題,和代碼不一致,所以這里并沒(méi)有直接使用他的時(shí)序圖,而是重新畫(huà)了。

可以結(jié)合上面兩個(gè)圖理解整個(gè)過(guò)程,上圖中的 a 對(duì)應(yīng)時(shí)序圖中的 2a,b 對(duì)應(yīng)時(shí)序圖中的 2b,c 對(duì)應(yīng)時(shí)序圖中的 G2.1。最下面白色部分對(duì)應(yīng)時(shí)序圖中 G1 的邏輯,即從 Etcd 獲取數(shù)據(jù),客戶端請(qǐng)求的處理是自上到下的,而數(shù)據(jù)返回是自下而上的。

注意

上述處理邏輯中存在很多的細(xì)節(jié),需要額外注意下

  1. 為 Watch API 修復(fù)了 Stale Read 的問(wèn)題(RV="" WatchList 功能),本質(zhì)上也是消除 List 的 Stale Read,只不過(guò)是在 Watch API 中實(shí)現(xiàn)的,這樣結(jié)合上一篇,不管是直接使用 List API 還是使用 WatchList 都能避免 Stale Read 的問(wèn)題;
  2. WatchCache Store 中的數(shù)據(jù)和 Cacher imcomming chan 數(shù)據(jù)是有交叉的,所以在 2a 處理完所有 Store 數(shù)據(jù)后記錄了最大的 RV 傳遞給 2b 在處理 imcomming chan 的數(shù)據(jù)時(shí)使用,event RV > RV 的非 BOOKMARK 事件才會(huì)發(fā)回客戶端,這樣是為了避免時(shí)間回流;
  3. CacheWatcher 的 input chan 中是不存在 RV < bookmarkAfterRV 的事件的,在 G2.1 從 Cacher incoming chan 消費(fèi)并發(fā)往所有 CacheWatcher input 的時(shí)候判斷了如果事件類型是 BOOKMARK 且 RV < bookmarkAfterRV,則直接丟棄此事件,因?yàn)?input chan 緩沖區(qū)大小有限,在其創(chuàng)建后 Cacher 就開(kāi)始往其 input 寫數(shù)據(jù),而開(kāi)始消費(fèi) input chan 是在 2a 處理完所有 Store 中的數(shù)據(jù)之后,中間存在一段時(shí)間差,事件的長(zhǎng)短和 Store 中的數(shù)據(jù)量有關(guān)系,丟棄不必要的 BOOKMARK 事件就可以緩解 input chan 的壓力,這里涉及到了為 input chan 添加事件的處理邏輯,里面包括多種特殊情況的處理,例如緩沖滿了如何處理避免因?yàn)閱蝹€(gè) CacheWatcher 而阻塞整個(gè)流程,發(fā)數(shù)據(jù)異常如何處理;
  4. 最終發(fā)回給客戶端的攜帶特定 Annotation 的 BOOKMARK 事件的 RV >= bookmarkAfterRV,這里非常值得注意,并不是等于 bookmarkAfterRV,原 KEP 時(shí)序圖中此處(2c)的描述是錯(cuò)誤的。根本原因在于 bookmark timer 的周期為 1 ~ 1.25s,也就是說(shuō)每 1 ~ 1.25s 產(chǎn)生一個(gè) BOOKMARK 事件,其 RV 是 incoming chan 最大 RV,正是由于這個(gè)時(shí)間間隔,結(jié)合 3 的描述,就會(huì)導(dǎo)致 G2.1 發(fā)送出去的第一個(gè)有效的 (進(jìn)入到 CacheWatcher input chan) BOOKMARK 事件的 RV >= bookmarkAfterRV。這也從側(cè)面說(shuō)明了最終在返回 bookmarkAfterRV BOOKMARK 事件之前返回的所有的攜帶有效負(fù)載的事件集合的最大 RV 也是 >= bookmarkAfterRV 的,即雖然標(biāo)記是 bookmarkAfterRV,但 List 的結(jié)果中包含比 bookmarkAfterRV 大的數(shù)據(jù)。 個(gè)人認(rèn)為此處還是可以再繼續(xù)優(yōu)化的,可以讓 List 的耗時(shí)減少一個(gè) bookmark timer 的周期,即 1 ~ 1.25s,只需要在 2b 處理非 BOOKMARK 事件時(shí)判斷 RV == bookmarkAfterRV 且尚未發(fā)送過(guò) bookmarkAfterRV BOOKMARK 事件,此時(shí)就可以直接返回一個(gè) bookmarkAfterRV BOOKMARK 給客戶端了,對(duì)于數(shù)據(jù)量較大,返回所有數(shù)據(jù)耗時(shí)超過(guò) Watch timeout 時(shí)間 1s 左右時(shí)可以降低超時(shí)的概率,避免重復(fù)執(zhí)行 WatchList 的過(guò)程,也能在一定程度上降低內(nèi)存消耗。

總結(jié)

本篇主要分析了 WatchList 的實(shí)現(xiàn)原理和邏輯,其中不乏一些細(xì)節(jié)處理,后續(xù)也會(huì)和社區(qū)就有關(guān)細(xì)節(jié)進(jìn)一步討論。在此 KEP 中同時(shí)還介紹了另外兩個(gè)用來(lái)降低 kube-apiserver 內(nèi)存壓力的修改,篇幅有限,將會(huì)在下一篇中進(jìn)行介紹,同時(shí)也會(huì)給出所有優(yōu)化工作做完前后的效果對(duì)比。敬請(qǐng)期待~

責(zé)任編輯:武曉燕 來(lái)源: 云原生散修
相關(guān)推薦

2025-04-30 10:55:46

2022-07-27 11:10:49

SPserverBRPC引擎

2021-03-03 08:18:54

Service組件

2022-05-09 08:35:43

面試產(chǎn)品互聯(lián)網(wǎng)

2015-09-17 13:09:48

預(yù)裝軟件毒瘤國(guó)產(chǎn)手機(jī)

2023-10-12 15:38:50

FreeDOS命令

2013-06-06 13:42:48

OSPF入門配置

2017-06-26 09:15:39

SQL數(shù)據(jù)庫(kù)基礎(chǔ)

2022-09-04 21:46:12

數(shù)據(jù)信息風(fēng)險(xiǎn)

2013-04-07 10:10:23

2023-12-27 06:48:49

KubernetesDevOpsHTTP

2019-07-02 14:17:18

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

2018-01-18 04:52:07

2016-11-28 16:23:23

戴爾

2010-12-22 12:00:48

軟件保護(hù)軟件授權(quán)

2010-02-06 15:31:18

ibmdwAndroid

2009-07-22 14:55:16

ibmdwAndroid

2012-04-26 10:48:01

iOS開(kāi)發(fā)互動(dòng)廣告

2020-10-27 06:39:14

智慧城市智慧旅游物聯(lián)網(wǎng)

2016-12-08 22:39:40

Android
點(diǎn)贊
收藏

51CTO技術(shù)棧公眾號(hào)

主站蜘蛛池模板: 日日骚av| 国产xxxx搡xxxxx搡麻豆 | 精品国产一级片 | 亚洲视频一区 | 综合久 | 亚洲成人久久久 | 国产一区91精品张津瑜 | 日韩中文一区二区三区 | 国产aaaaav久久久一区二区 | 亚洲成人精品久久 | 久夜精品 | 成人在线中文 | 亚洲精品99| 久久国内精品 | 麻豆视频国产在线观看 | 91视频a| 丁香五月缴情综合网 | 国产www.| 中文字幕高清免费日韩视频在线 | 高清国产午夜精品久久久久久 | 成人在线小视频 | 99福利视频| 97超在线视频 | 91高清在线观看 | 99精品观看 | 国产黄色麻豆视频 | 国产在线观看一区 | 国产欧美精品一区二区三区 | 日韩影院一区 | 毛片a级| 欧美日韩三级 | 国产电影一区二区三区爱妃记 | 午夜精品一区二区三区在线视频 | 精品国产伦一区二区三区观看说明 | 日韩精品 电影一区 亚洲 | 中文字幕视频在线免费 | 国产一区高清 | 在线观看第一页 | av香蕉 | 亚洲精品久久久久久一区二区 | 一区二区免费视频 |