TiDB 在知乎萬億量級業(yè)務(wù)數(shù)據(jù)下的實踐和挑戰(zhàn)
作者:孫曉光,知乎搜索后端負責人,目前承擔知乎搜索后端架構(gòu)設(shè)計以及工程團隊的管理工作。曾多年從事私有云相關(guān)產(chǎn)品開發(fā)工作關(guān)注云原生技術(shù),TiKV 項目 Committer。
本文根據(jù)孫曉光老師在 TiDB TechDay 2019 北京站上的演講整理。
本次分享首先將從宏觀的角度介紹知乎已讀服務(wù)的業(yè)務(wù)場景中的挑戰(zhàn)、架構(gòu)設(shè)計思路,然后將從微觀的角度介紹其中的關(guān)鍵組件的實現(xiàn),最后分享在整個過程中 TiDB 幫助我們解決了什么樣的問題,以及 TiDB 是如何幫助我們將龐大的系統(tǒng)全面云化,并推進到一個非常理想的狀態(tài)的。
一、業(yè)務(wù)場景
知乎從問答起步,在過去的 8 年中逐步成長為一個大規(guī)模的綜合性知識內(nèi)容平臺,目前,知乎上有多達 3000 萬個問題,共收獲了超過 1.3 億個回答,同時知乎還沉淀了數(shù)量眾多的文章、電子書以及其他付費內(nèi)容,目前注冊用戶數(shù)是 2.2 億,這幾個數(shù)字還是蠻驚人的。我們有 1.3 億個回答,還有更多的專欄文章,所以如何高效的把用戶最感興趣的優(yōu)質(zhì)內(nèi)容分發(fā)他們,就是非常重要的問題。
圖 1
知乎首頁是解決流量分發(fā)的一個關(guān)鍵的入口,而已讀服務(wù)想要幫助知乎首頁解決的問題是,如何在首頁中給用戶推薦感興趣的內(nèi)容,同時避免給用戶推薦曾經(jīng)看過的內(nèi)容。已讀服務(wù)會將所有知乎站上用戶深入閱讀或快速掠過的內(nèi)容記錄下來長期保存,并將這些數(shù)據(jù)應用于首頁推薦信息流和個性化推送的已讀過濾。圖 2 是一個典型的流程:
圖 2
當用戶打開知乎進入推薦頁的時候,系統(tǒng)向首頁服務(wù)發(fā)起請求拉取“用戶感興趣的新內(nèi)容”,首頁根據(jù)用戶畫像,去多個召回隊列召回新的候選內(nèi)容,這些召回的新內(nèi)容中可能有部分是用戶曾經(jīng)看到過的,所以在分發(fā)給用戶之前,首頁會先把這些內(nèi)容發(fā)給已讀服務(wù)過濾,然后做進一步加工并最終返回給客戶端,其實這個業(yè)務(wù)流程是非常簡單的。
圖 3
這個業(yè)務(wù)第一個的特點是可用性要求非常高,因為首頁可能是知乎最重要的流量分發(fā)渠道。第二個特點是寫入量非常大,峰值每秒寫入 40k+ 條記錄,每日新增記錄近 30 億條。并且我們保存數(shù)據(jù)的時間比較長,按照現(xiàn)在產(chǎn)品設(shè)計需要保存三年。整個產(chǎn)品迭代到現(xiàn)在,已經(jīng)保存了約一萬三千億條記錄,按照每月近一千億條的記錄增長速度,大概兩年之后,可能要膨脹到三萬億的數(shù)據(jù)規(guī)模。
圖 4
這個業(yè)務(wù)的查詢端要求也很高。首先,產(chǎn)品吞吐高。用戶在線上每次刷新首頁,至少要查一次,并且因為有多個召回源和并發(fā)的存在,查詢吞吐量還可能放大。峰值時間首頁每秒大概產(chǎn)生 3 萬次獨立的已讀查詢,每次查詢平均要查 400 個文檔,長尾部分大概 1000 個文檔,也就是說,整個系統(tǒng)峰值平均每秒大概處理 1200 萬份文檔的已讀查詢。在這樣一個吞吐量級下,要求的響應時間還比較嚴格,要求整個查詢響應時間(端到端超時)是 90ms,也就意味著最慢的長尾查詢都不能超過 90ms。還有一個特點是,它可以容忍 false positive,意味著有些內(nèi)容被我們過濾掉了,但是系統(tǒng)仍然能為用戶召回足夠多的他們可能感興趣的內(nèi)容,只要 false positive rate 被控制在可接受的范圍就可以了。
二、架構(gòu)設(shè)計
由于知乎首頁的重要性,我們在設(shè)計這個系統(tǒng)的時候,考慮了三個設(shè)計目標:高可用、高性能、易擴展。首先,如果用戶打開知乎首頁刷到大量已經(jīng)看過的內(nèi)容,這肯定不可接受,所以對已讀服務(wù)的第一個要求是「高可用」。第二個要求是「性能高」,因為業(yè)務(wù)吞吐高,并且對響應時間要求也非常高。第三點是這個系統(tǒng)在不斷演進和發(fā)展,業(yè)務(wù)也在不斷的更新迭代,所以系統(tǒng)的「擴展性」非常重要,不能說今天能支撐,明天就支撐不下來了,這是沒法接受的。
接下來從這三個方面來介紹我們具體是如何設(shè)計系統(tǒng)架構(gòu)的。
2.1 高可用
圖 5
當我們討論高可用的時候,也意味著我們已經(jīng)意識到故障是無時無刻都在發(fā)生的,想讓系統(tǒng)做到高可用,首先就要有系統(tǒng)化的故障探測機制,檢測組件的健康狀況,然后設(shè)計好每一個組件的自愈機制,讓它們在故障發(fā)生之后可以自動恢復,無需人工干預。最后我們希望用一定的機制把這些故障所產(chǎn)生的變化隔離起來,讓業(yè)務(wù)側(cè)盡可能對故障的發(fā)生和恢復無感知。
2.2 高性能
圖 6
對常見的系統(tǒng)來說,越核心的組件往往狀態(tài)越重擴展的代價也越大,層層攔截快速降低需要深入到核心組件的請求量對提高性能是非常有效的手段。首先我們通過緩沖分 Slot 的方式來擴展集群所能緩沖的數(shù)據(jù)規(guī)模。接著進一步在 Slot 內(nèi)通過多副本的方式提升單個 Slot 緩沖數(shù)據(jù)集的讀取吞吐,將大量的請求攔截在系統(tǒng)的緩沖層進行消化。如果請求不可避免的走到了最終的數(shù)據(jù)庫組件上,我們還可以利用效率較高的壓縮來繼續(xù)降低落到物理設(shè)備上的 I/O 壓力。
2.3 易擴展
圖 7
提升系統(tǒng)擴展性的關(guān)鍵在于減少有狀態(tài)組件的范圍。在路由和服務(wù)發(fā)現(xiàn)組件的幫助下,系統(tǒng)中的無狀態(tài)組件可以非常輕松的擴展擴容,所以通過擴大無狀態(tài)服務(wù)的范圍,收縮重狀態(tài)服務(wù)的比例,可以顯著的幫助我們提升整個系統(tǒng)的可擴展性。除此之外,如果我們能夠設(shè)計一些可以從外部系統(tǒng)恢復狀態(tài)的弱狀態(tài)服務(wù),部分替代重狀態(tài)組件,這樣可以壓縮重狀態(tài)組件的比例。隨著弱狀態(tài)組件的擴大和重狀態(tài)組件的收縮,整個系統(tǒng)的可擴展性可以得到進一步的提升。
2.4 已讀服務(wù)最終架構(gòu)
在高可用、高性能和易擴展的設(shè)計理念下,我們設(shè)計實現(xiàn)了已讀服務(wù)的架構(gòu),圖 8 是已讀服務(wù)的最終架構(gòu)。
圖 8
首先,上層的客戶端 API 和 Proxy 是完全無狀態(tài)可隨時擴展的組件。最底層是存儲全部狀態(tài)數(shù)據(jù)的 TiDB,中間這些組件都是弱狀態(tài)的組件,主體是分層的 Redis 緩沖。除了 Redis 緩沖之外,我們還有一些其他外部組件配合 Redis 保證 Cache 的一致性,這里面的細節(jié)會在下一章詳述。
從整個系統(tǒng)來看,TiDB 這層自身已經(jīng)擁有了高可用的能力,它是可以自愈的,系統(tǒng)中無狀態(tài)的組件非常容易擴展,而有狀態(tài)的組件中弱狀態(tài)的部分可以通過 TiDB 中保存的數(shù)據(jù)恢復,出現(xiàn)故障時也是可以自愈的。此外系統(tǒng)中還有一些組件負責維護緩沖一致性,但它們自身是沒有狀態(tài)的。所以在系統(tǒng)所有組件擁有自愈能力和全局故障監(jiān)測的前提下,我們使用 Kubernetes 來管理整個系統(tǒng),從而在機制上確保整個服務(wù)的高可用。
三、關(guān)鍵組件
3.1 Proxy
圖 9
Proxy 層是無狀態(tài)的,設(shè)計同常見的 Redis 代理相似,從實現(xiàn)角度看也非常簡單。首先我們會基于用戶緯度將緩沖拆分成若干 Slot,每個 Slot 里有多個 Cache 的副本,這些多副本一方面可以提升我們整個系統(tǒng)的可用性,另外一方面也可以分攤同一批數(shù)據(jù)的讀取壓力。這里面也有一個問題,就是 Cache 的副本一致性的如何保證?我們在這里選擇的是「會話一致性」,也就是一個用戶在一段時間內(nèi)從同一個入口進來,就會綁定在這一個 Slot 里面的某個副本上,只要沒有發(fā)生故障,這個會話會維持在上面。
如果一個 Slot 內(nèi)的某個副本發(fā)生故障,Proxy 首先挑這個 Slot 內(nèi)的其他的副本繼續(xù)提供服務(wù)。更極端的情況下,比如這個 Slot 內(nèi)所有副本都發(fā)生故障,Proxy 可以犧牲系統(tǒng)的性能,把請求打到另外一個完全不相干的一個 Slot 上,這個 Slot 上面沒有當前請求對應數(shù)據(jù)的緩存,而且拿到結(jié)果后也不會緩存相應的結(jié)果。我們付出這樣的性能代價獲得的收益是系統(tǒng)可用性變得更高,即便 Slot 里的所有的副本同時發(fā)生故障,依舊不影響系統(tǒng)的可用性。
3.2 Cache
對于緩沖來說,非常重要的一點就是如何提升緩沖利用率。
第一點是如何用同樣的資源緩沖更大量的數(shù)據(jù)。在由「用戶」和「內(nèi)容類型」和「內(nèi)容」所組成的空間中,由于「用戶」維度和「內(nèi)容」維度的基數(shù)非常高,都在數(shù)億級別,即使記錄數(shù)在萬億這樣的數(shù)量級下,數(shù)據(jù)在整個三維空間內(nèi)的分布依然非常稀疏。如圖 10 左半部分所示。
圖 10
考慮到目前知乎站上沉淀的內(nèi)容量級巨大,我們可以容忍 false positive 但依舊為用戶召回到足夠多可能會感興趣的內(nèi)容?;谶@樣的業(yè)務(wù)特點,我們將數(shù)據(jù)庫中存儲的原始數(shù)據(jù)轉(zhuǎn)化為更加致密的 BloomFilter 緩沖起來,這極大的降低了內(nèi)存的消耗在相同的資源狀況下可以緩沖更多的數(shù)據(jù),提高緩存的命中率。
提升緩存命中率的方式有很多種,除了前面提到的提升緩存數(shù)據(jù)密度增加可緩沖的數(shù)據(jù)量級之外,我們還可以通過避免不必要的緩存失效來進一步的提升緩存的效率。
圖 11
一方面我們將緩存設(shè)計為 write through cache 使用原地更新緩存的方式來避免 invalidate cache 操作,再配合數(shù)據(jù)變更訂閱我們可以在不失效緩沖的情況下確保同一份數(shù)據(jù)的多個緩沖副本能在很短的時間內(nèi)達成最終一致。
另一方面得益于 read through 的設(shè)計,我們可以將對同一份數(shù)據(jù)的多個并發(fā)查詢請求轉(zhuǎn)化成一次 cache miss 加多次緩沖讀取(圖 11 右半部分),進一步提升緩存的命中率降低穿透到底層數(shù)據(jù)庫系統(tǒng)的壓力。
接下來再分享一些不單純和緩沖利用率相關(guān)的事情。眾所周知,緩沖特別怕冷,一旦冷了, 大量的請求瞬間穿透回數(shù)據(jù)庫,數(shù)據(jù)庫很大概率都會掛掉。在系統(tǒng)擴容或者迭代的情況下,往往需要加入新的緩沖節(jié)點,那么如何把新的緩沖節(jié)點熱起來呢?如果是類似擴容或者滾動升級這種可以控制速度的情況,我們可以控制開放流量的速度,讓新的緩沖節(jié)點熱起來,但當系統(tǒng)發(fā)生故障的時候,我們就希望這個節(jié)點非常快速的熱起來。 所以在我們這個系統(tǒng)和其他的緩沖系統(tǒng)不大一樣的是,當一個新節(jié)點啟動起來,Cache 是冷的,它會馬上從旁邊的 Peer 那邊 transfer 一份正在活躍的緩存狀態(tài)過來,這樣就可以非常快的速度熱起來,以一個熱身的狀態(tài)去提供線上的服務(wù)(如圖 12)。
圖 12
另外,我們可以設(shè)計分層的緩沖,每一層緩沖可以設(shè)計不同的策略,分別應對不同層面的問題,如圖 13 所示,可以通過 L1 和 L2 分別去解決空間層面的數(shù)據(jù)熱度問題和時間層面的熱度問題,通過多層的 Cache 可以逐層的降低穿透到下一層請求的數(shù)量,尤其是當我們發(fā)生跨數(shù)據(jù)中心部署時,對帶寬和時延要求非常高,如果有分層的設(shè)計,就可以在跨數(shù)據(jù)中心之間再放一層 Cache,減少在穿透到另外一個數(shù)據(jù)中心的請求數(shù)量。
圖 13
為了讓業(yè)務(wù)之間不互相影響并且針對不同業(yè)務(wù)的數(shù)據(jù)訪問特征選擇不同的緩沖策略,我們還進一步提供了 Cache 標簽隔離的機制來隔離離線寫入和多個不同的業(yè)務(wù)租戶的查詢。剛剛說的知乎已讀服務(wù)數(shù)據(jù),在后期已經(jīng)不只是給首頁提供服務(wù)了,還同時為個性化推送提供服務(wù)。個性化推送是一個典型的離線任務(wù),在推送內(nèi)容前去過濾一下用戶是否看過。雖然這兩個業(yè)務(wù)訪問的數(shù)據(jù)是一樣的,但是它們的訪問特征和熱點是完全不一樣的,相應的緩沖策略也不一樣的。于是我們在做分組隔離機制(如圖 14),緩沖節(jié)點以標簽的方式做隔離,不同的業(yè)務(wù)使用不同的緩沖節(jié)點,不同緩沖節(jié)點搭配不同的緩沖策略,達到更高的投入產(chǎn)出比,同時也能隔離各個不同的租戶,防止他們之間互相產(chǎn)生影響。
圖 14
3.3 Storage
圖 15
存儲方面,我們最初用的是 MySQL,顯然這么大量的數(shù)據(jù)單機是搞不定的,所以我們使用了分庫分表 + MHA 機制來提升系統(tǒng)的性能并保障系統(tǒng)的高可用,在流量不太大的時候還能忍受,但是在當每月新增一千億數(shù)據(jù)的情況下,我們心里的不安與日俱增,所以一直在思考怎樣讓系統(tǒng)可持續(xù)發(fā)展、可維護,并且開始選擇替代方案。這時我們發(fā)現(xiàn) TiDB 兼容了 MySQL,這對我們來說是非常好的一個特點,風險非常小,于是我們開始做遷移工作。遷移完成后,整個系統(tǒng)最弱的“擴展性”短板就被補齊了。
3.4 性能指標
圖 16
現(xiàn)在整個系統(tǒng)都是高可用的,隨時可以擴展,而且性能變得更好。圖 16 是前兩天我取出來的性能指標數(shù)據(jù),目前已讀服務(wù)的流量已達每秒 4 萬行記錄寫入,3 萬獨立查詢和 1200 萬個文檔判讀,在這樣的壓力下已讀服務(wù)響應時間的 P99 和 P999 仍然穩(wěn)定的維持在 25ms 和 50ms,其實平均時間是遠低于這個數(shù)據(jù)的。這個意義在于已讀服務(wù)對長尾部分非常敏感,響應時間要非常穩(wěn)定,因為不能犧牲任何一位用戶的體驗,對一位用戶來說來說超時了就是超時了。
四、All about TiDB
最后分享一下我們從 MySQL 遷移到 TiDB 的過程中遇到的困難、如何去解決的,以及 TiDB 3.0 發(fā)布以后我們在這個快速迭代的產(chǎn)品上,收獲了什么樣的紅利。
4.1 MySQL to TiDB
)
圖 17
現(xiàn)在其實整個 TiDB 的數(shù)據(jù)遷移的生態(tài)工具已經(jīng)很完善,我們打開 TiDB DM 收集 MySQL 的增量 binlog 先存起來,接著用 TiDB Lightning 快速把歷史數(shù)據(jù)導入到 TiDB 中,當時應該是一萬一千億左右的記錄,導入總共用時四天。這個時間還是非常震撼的,因為如果用邏輯寫入的方式至少要花一個月。當然四天也不是不可縮短,那時我們的硬件資源不是特別充足,選了一批機器,一批數(shù)據(jù)導完了再導下一批,如果硬件資源夠的話,可以導入更快,也就是所謂“高投入高產(chǎn)出”,如果大家有更多的資源,那么應該可以達到更好的效果。在歷史數(shù)據(jù)全部導入完成之后,就需要開啟 TiDB DM 的增量同步機制,自動把剛才存下來的歷史增量數(shù)據(jù)和實時增量數(shù)據(jù)同步到 TiDB 中,并近實時的維持 TiDB 和 MySQL 數(shù)據(jù)的一致。
在遷移完成之后,我們就開始小流量的讀測試,剛上線的時候其實發(fā)現(xiàn)是有問題的,Latency 無法滿足要求,剛才介紹了這個業(yè)務(wù)對 Latency 特別敏感,稍微慢一點就會超時。這時 PingCAP 伙伴們和我們一起不停去調(diào)優(yōu)、適配,解決 Latency 上的問題。圖 18 是我們總結(jié)的比較關(guān)鍵的經(jīng)驗。
圖 18
第一,我們把對 Latency 敏感的部分 Query 布了一個獨立的 TiDB 隔離開,防止特別大的查詢在同一個 TiDB 上影響那些對 Latency 敏感的的 Query。第二,有些 Query 的執(zhí)行計劃選擇不是特別理想,我們也做了一些 SQL Hint,幫助執(zhí)行引擎選擇一個更加合理的執(zhí)行計劃。除此之外,我們還做了一些更微觀的優(yōu)化,比如說使用低精度的 TSO,還有包括復用 Prepared Statement 進一步減少網(wǎng)絡(luò)上的 roundtrip,最后達到了很好的效果。
圖 19
這個過程中我們還做了一些開發(fā)的工作,比如 binlog 之間的適配。因為這套系統(tǒng)是靠 binlog 變更下推來維持緩沖副本之間的一致性,所以 binlog 尤為重要。我們需要把原來 MySQL 的 binlog 改成 TiDB 的 binlog,但是過程中遇到了一些問題,因為 TiDB 作為一個數(shù)據(jù)庫產(chǎn)品,它的 binlog 要維持全局的有序性的排列,然而在我們之前的業(yè)務(wù)中由于分庫分表,我們不關(guān)心這個事情,所以我們做了些調(diào)整工作,把之前的 binlog 改成可以用 database 或者 table 來拆分的 binlog,減輕了全局有序的負擔,binlog 的吞吐也能滿足我們要求了。同時,PingCAP 伙伴們也做了很多 Drainer 上的優(yōu)化,目前 Drainer 應該比一兩個月前的狀態(tài)好很多,不論是吞吐還是 Latency 都能滿足我們現(xiàn)在線上的要求。
最后一點經(jīng)驗是關(guān)于資源評估,因為這一點可能是我們當時做得不是特別好的地方。最開始我們沒有特別仔細地想到底要多少資源才能支撐同樣的數(shù)據(jù)。最初用 MySQL 的時候,為了減少運維負擔和成本,我們選擇了“1 主 1 從”方式部署 ,而 TiDB 用的 Raft 協(xié)議要求至少三個副本,所以資源要做更大的準備,不能指望用同樣的資源來支撐同樣的業(yè)務(wù),一定要提前準備好對應的機器資源。另外,我們的業(yè)務(wù)模式是一個非常大的聯(lián)合主鍵,這個聯(lián)合主鍵在 TiDB 上非聚簇索引,又會導致數(shù)據(jù)更加龐大,也需要對應準備出更多的機器資源。最后,因為 TiDB 是存儲與計算分離的架構(gòu),所以網(wǎng)絡(luò)環(huán)境一定要準備好。當這些資源準備好,最后的收益是非常明顯的。
4.2 TiDB 3.0
在知乎內(nèi)部采用與已讀服務(wù)相同的技術(shù)架構(gòu)我們還支撐了一套用于反作弊的風控類業(yè)務(wù)。與已讀服務(wù)極端的歷史數(shù)據(jù)規(guī)模不同,反作弊業(yè)務(wù)有著更加極端的寫入吞吐但只需在線查詢最近 48 小時入庫的數(shù)據(jù)(詳細對比見圖 20)。
圖 20
那么 TiDB 3.0 的發(fā)布為我們這兩個業(yè)務(wù),尤其是為反作弊這個業(yè)務(wù),帶來什么樣的可能呢?
首先我們來看看已讀服務(wù)。已讀服務(wù)寫讀吞吐也不算小,大概 40k+,TiDB 3.0 的 gRPC Batch Message 和多線程 Raft store,能在這件事情上起到很大的幫助。另外,Latency 這塊,我剛才提到了,就是我們寫了非常多 SQL Hint 保證 Query 選到最優(yōu)的執(zhí)行計劃,TiDB 3.0 有 Plan Management 之后,我們再遇到執(zhí)行計劃相關(guān)的問題就無需調(diào)整代碼上線,直接利用 Plan Management 進行調(diào)整就可以生效了,這是一個非常好用的 feature。
剛才馬曉宇老師詳細介紹了 TiFlash,在 TiDB DevCon 2019 上第一次聽到這個產(chǎn)品的時候就覺得特別震撼,大家可以想象一下,一萬多億條的數(shù)據(jù)能挖掘出多少價值, 但是在以往這種高吞吐的寫入和龐大的全量數(shù)據(jù)規(guī)模用傳統(tǒng)的 ETL 方式是難以在可行的成本下將數(shù)據(jù)每日同步到 Hadoop 上進行分析的。而當我們有 TiFlash,一切就變得有可能了。
圖 21
再來看看反作弊業(yè)務(wù),它的寫入更極端,這時 TiDB 3.0 的 Batch message 和多線程 Raft Store 兩個特性可以讓我們在更低的硬件配置情況下,達到之前同樣的效果。另外反作弊業(yè)務(wù)寫的記錄偏大,TiDB 3.0 中包含的新的存儲引擎 Titan,就是來解決這個問題的,我們從 TiDB 3.0.0- rc1 開始就在反作弊業(yè)務(wù)上將 TiDB 3.0 引入到了生產(chǎn)環(huán)境,并在 rc2 發(fā)布不久之后開啟了 Titan 存儲引擎,下圖右半部分可以看到 Titan 開啟前后的寫入/查詢 Latency 對比,當時我們看到這個圖的時候都非常非常震撼,這是一個質(zhì)的變化。
圖 22
另外,我們也使用了 TiDB 3.0 中 Table Partition 這個特性。通過在時間維度拆分 Table Partition,可以控制查詢落到最近的 Partition 上,這對查詢的時效提升非常明顯。
五、總結(jié)
最后簡單總結(jié)一下我們開發(fā)這套系統(tǒng)以及在遷移到 TiDB 過程中的收獲和思考。
圖 23
首先開發(fā)任何系統(tǒng)前一定先要理解這個業(yè)務(wù)特點,對應設(shè)計更好的可持續(xù)支撐的方案,同時希望這個架構(gòu)具有普適性,就像已讀服務(wù)的架構(gòu),除了支撐知乎首頁,還可以同時支持反作弊的業(yè)務(wù)。
另外,我們大量應用了開源軟件,不僅一直使用,還會參與一定程度的開發(fā),在這個過程中我們也學到了很多東西。所以我們應該不僅以用戶的身份參與社區(qū),甚至還可以為社區(qū)做更多貢獻,一起把 TiDB 做的更好、更強。
最后一點,我們業(yè)務(wù)系統(tǒng)的設(shè)計可能看上去有點過于復雜,但站在今天 Cloud Native 的時代角度,即便是業(yè)務(wù)系統(tǒng),我們也希望它能像 Cloud Native 產(chǎn)品一樣,原生的支持高可用、高性能、易擴展,我們做業(yè)務(wù)系統(tǒng)也要以開放的心態(tài)去擁抱新技術(shù),Cloud Native from Ground Up。