作者:vivo 網際網路平臺產品研發團隊 - He Zhichuang、Han Lei
手機雲服務目前作為每家手機廠商必備的一項基礎服務,其服務能力和服務質量對使用者來說可以說是非常重要。使用者將自己大量的資訊資料儲存在雲端,那我們的雲端服務如何保證服務的穩定和資料的安全,以及如何應對越來越多使用者群體的使用?本文將主要介紹 vivo 手機雲服務系統的建設歷程。
幾乎每家手機廠商都為使用者提供了資訊儲存的雲服務能力。通過一個賬號,使用者可以將手機系統中的各種常用的資訊備份到雲端,以便後續在合適的時間點檢視或恢復自身的資料。然而由於使用者量級巨大,服務在設計系統的時候需要考慮的因素特別多,比如如何保證服務的穩定性,如何保證大檔案的傳輸效率,以及如何保證使用者檔案的資料永續性等等。
除此之外,隨著越來越多的終端使用者開始使用vivo雲服務,儲存和計算的成本也與日俱增。可能有部分人瞭解,某些手機廠商的雲服務產品年度虧損數億級別,而主要成本之處來自使用者私人檔案的儲存成本。
另外,在安全方面,雲服務在這塊需要承擔的使命更是重中之重。某些廠商的雲服務曾經出現過使用者資料洩露,居然可以通過搜尋引擎直接查詢到使用者的私人檔案,這種事件一旦出現,對企業品牌的打擊和影響可以說是非常巨大。
如上所述,雲服務在建設過程中可以說是困難重重,那麼vivo雲服務在建設過程中,又是如何兼顧產品功能、資源成本、服務穩定性、資料安全等等諸多因素而進行設計的?且聽後文細細分解。
當今智慧裝置發展迅速,各個手機廠商相繼推出了PAD、智慧手錶等裝置。因此不同裝置之間的資料互通訴求也隨之而來,一個帳號實現資料互通。
拿vivo為例,vivo帳號可以同時在vivo手機、vivo PAD、PC上登入,使用者可以在手機、PAD、PC上同時對聯絡人、日曆等內容進行編輯,一端編輯,多端可見。
這種多裝置資料同步互通就是雲服務的一項核心功能。當前雲服務支援同步的資料項:聯絡人、日曆、便籤、書籤、黑名單、藍芽、WLAN,後續會支援更多的資料項。
手機行業功能更新迭代很快,新的亮點功能會吸參照戶購買新機。但是新機購買回來後,各種資料的設定、新增對使用者來說是個繁瑣、頭疼的事情。
為了方便使用者將舊手機的資料遷移到新手機上來,手機廠商提供了一些資料遷移工具。如我司的互傳,新老手機放在一起通過藍芽可以方便的將資料匯入新手機上。但是互傳必須要求2個手機在一起,如果使用者舊手機不在身邊呢?
此場景下,雲服務提供的整機打包功能很好的解決了此痛點。使用者在使用舊手機期間,可以開啟雲服務的整機備份開關,雲服務會自動將使用者手機資料打成封包備份至雲端。
在使用者購買新手機換機時,可以通過雲服務快速選擇老手機的打包資料進行恢復,方便快捷。
雲盤是一種專業的網際網路儲存工具,是網際網路雲技術的產物,它通過網際網路為企業和個人提供資訊的儲存,讀取,下載等服務。具有安全穩定、海量儲存的特點。
在vivo雲服務中,除了諸如聯絡人、簡訊等資料型別內容的備份恢復能力之外,檔案型別的雲端儲存能力,即雲盤的能力同樣重要。
使用者可以將自己本地重要的圖片、視訊、檔案等重要檔案備份到雲端,以便後續可以在雲端後者在其他裝置上可以存取到該檔案,同時藉助於雲盤的能力,使用者也可以方便快捷的釋放整理本地空間。
除此之外,雲盤還提供了豐富的檔案周邊功能,例如壓縮檔案的線上解壓,視訊的線上播放,以及檔案線上共同作業等等。
雲服務資料同步的方案採用的是類似於Git版本管理的概念,主要涉及2個行為:
推資料:將本地裝置增量資料推播至雲端。
拉資料:將雲端增量資料拉取至本地。
主要需要了解的有以下2點:
增量資料識別;
資料衝突處理。
(1)增量資料識別
雲服務採用的是基於資料版本的識別方案:雲端每條資料都有自身的版本號,版本號逐步遞增。
主要同步流程如下圖:
如圖可見,增量資料同步過程並不複雜,整個流程總結如下:
使用者端獲取雲端當前最大的資料版本sv;
若使用者端本地資料最大版本lv < sv,則證明雲端資料有更新,使用者端需要拉取雲端增量資料;
若lv = sv,則使用者端判斷本地是否存在增量更新資料,若有則將本地增量資料推播到雲端。
(2)資料衝突處理
資料衝突出現在多裝置同時使用的過程中,同時對同一條資料進行操作,造成資料衝突的情況。
因此同步資料流程需要考慮資料衝突的場景。
常見的衝突解決方案有2種:a、自動為使用者解決衝突。b、使用者手動自行解決衝突。
自動為使用者解決衝突一般有以下方案:
以最新的資料修改時間為準,以修改時間最遲的裝置的資料為準。(多裝置時鐘無法統一問題,後面上報的資料可能並不是使用者實際上最後修改的)
2條資料都保留。(會給使用者造成資料重複的錯覺,影響體驗)
使用者手動自行解決衝突:
參照git的衝突處理方式,衝突資料展示給使用者,由使用者自行選擇內容的存留,最後將最終資料推播到雲端。
由於雲服務對接了很多不同模組的資料:聯絡人、日程、瀏覽器書籤,不同資料的特性不一樣,每種資料的衝突處理的規則也不一樣。因此雲服務採用了將衝突資料返回給業務模組,供業務模組自行解決的策略,於業務方採用上述哪種解決方式,由業務方自行決策。
雲服務採用的是將本地不同模組的資料打包成檔案,上傳至雲盤的方案。
通過樹形結構,將整個包、不同模組、不同模組的資料檔案進行關聯,恢復資料時,通過父包parentId即可獲取到所有的資料檔案的metaId,進行恢復即可。
此方案的優點:方便快速擴充套件備份手機其他模組的資料,伺服器基本上不需要進行改造。
當然此方案也存在劣勢:裝置不同模組的資料格式對伺服器屬於黑盒,伺服器難以針對模組的資料做實時的解析和展示。
相對於資料專案的同步備份,雲盤模組主要聚焦的是檔案型別的雲端存取。
和普通業務模型相比,雲盤業務的顯著特點是邏輯複雜,需要考慮的細節很多:例如空間佔用、資料安全、大檔案傳輸效率等等,因此整個的系統設計更加複雜。
1、物件儲存簡介
《物件儲存》是由雲端儲存供應商提供的一套基於物件的海量儲存服務,一般可以為使用者可以提供海量、安全、高可靠、低成本的資料儲存能力。
在vivo雲服務的儲存邏輯中,使用者的圖片、視訊、音訊等檔案目前均儲存在物件儲存服務中。
由於早期vivo內部並無自建的物件儲存能力,故一開始這部分資料均存放在公有云,隨著近兩年vivo自建物件儲存能力的完善,目前公有云資料已完全遷移到了自建儲存。
2、雲盤系統架構
如上圖所示,雲盤涉及到的周邊模組眾多,但是最核心的還是後設資料模組、空間管理模組、檔案處理這三個模組,概述如下:
後設資料模組:主要用來描述檔案的屬性,例如檔案的名稱,檔案的大小,媒體檔案的長寬高等等。更抽象的,後設資料模組儲存了除了檔案實體內容之外的所有資訊。
但是,為了系統後續的可延伸性,我們針對後設資料模組還進行了「動靜」分離。
具體如下:
不同的業務所關注的後設資料資訊不盡相同,比如除了一些名稱大小這些公共屬性外,雲相簿業務還會關注諸如檔案拍攝時間,exif中的特定欄位等等,而這些欄位在別的業務中卻不會使用。
所以我們繼續將靜態的不會變化的公共資訊繼續進行了一層沉降,即上圖中的公用後設資料層。這一層存放了檔案的大小、狀態、檔案摘要值,儲存在物件儲存的路勁等核心內容。
空間模組:和大部分手機廠商一樣,雲服務預設會允許每個使用者免費使用的5G空間,如果儲存總量級超出了5G,那麼使用者則需要購買VIP以提升空間容量。
那麼關於使用者空間資訊的管理,我們有一個統一的空間模組進行收納管控。
檔案處理模組:此模組主要提供使用者檔案資料的上下行能力。比如檔案的斷點上傳下載能力,媒體檔案的縮圖處理能力,壓縮包檔案的線上解壓能力等等,都由該服務承載。
下面,我們主要來了解下最核心的檔案上傳流程,如下圖所示。
在實際的業務處理中,檔案上傳的整個流程其實遠遠不止上述時序圖這麼簡單,比如檔案縮圖的處理,比如使用者身份的校驗,或者是風險檔案的識別,加密的處理等等。
由於雲服務業務使用使用者量級巨大,所以在關係型資料庫的設計上,也要考慮後續頻繁擴容的場景。
關於雲服務的分庫分表實踐,這裡不再展開描述,感興趣的可以參考這篇文章:你分庫分表的姿勢對麼?——詳談水平分庫分表
和普通的業務資料互動相比,檔案的上下行動作就顯得特別"笨重",因為每次處理都要傳輸大量的檔案報文。
那試想,如果使用者在上傳一個上G的檔案,突然遇到了弱網環境而中斷了連結,那下次恢復連結之後,還需要從頭開始上傳,這樣無非會對整體檔案的傳輸體驗帶來非常大的影響。
在使用者端進行檔案上傳時,我們會約定一個分片大小閾值。我們會將檔案切割成一組組大小不超過閾值的檔案片段,然後對每個片段進行傳輸。
這樣如果端上遇到了弱網環境,那麼我們也只要對失敗的分片進行重傳即可,大大提升了整體檔案傳輸的效能。
同樣,使用者端進行檔案下載時,如果下載一半網路斷開了,那麼下次又需要對整個檔案進行重新下載。
所以,vivo雲盤在對檔案下載時,也使用了斷點下載能力,主要基於HTTP的Range頭資訊,對需要的檔案資源進行定位擷取。
因為前文描述了檔案在上傳的時候通過分片技術將檔案進行了拆分,那麼在斷點下載的時候,可以通過Range中的範圍計算得到具體涉及的儲存路勁,無需進行多餘的IO操作。
當前雲服務使用者資料規模頗大,諸如後設資料類儲存在資料庫中的資料總條數已經超過了5000億、而檔案類總佔用空間也超過了百PB。
如此海量資料的儲存,每年耗費的磁碟成本和資料庫成本都是一筆不小的數目,因此雲服務在節省成本上也做了不少動作。
隨著在網使用者的量級越來越大,使用者每天需要備份的檔案數量也呈日趨增大,那麼如何從技術層級進行降本呢?
我們這邊主要進行了以下幾個方面的探索和挖掘。
在vivo物件儲存自建完成之前,雲盤也是將資料存放在公有云的物件儲存上。
儲存分級技術主要是將不同的資料採取不同的儲存方式分別儲存在不同效能的儲存裝置上。
一般來說,公有云將物件儲存的儲存分成三種型別(部分公有云會有四層或更多),即標準儲存,低頻儲存,歸檔儲存。
以下為某公有云的儲存分級報價情況:
在標準儲存和低頻儲存的選擇方面,我們假設:S為當前儲存總量,G為每月取回總大小,那麼經過資料計算,我們可以推匯出:
即如果每月的檔案取出率小於123%,則使用標準能有更優的成本,而如果大於123%,則應該使用低頻儲存。
然而對於使用者行為進行分析,使用者對檔案進行儲存後,後續存取原始檔的概率非常小,但是使用者可能會經常到雲端去檢視自己的檔案,這個時候展示的大部分是縮圖。
於是我們將原始檔和縮圖進行分離,將原始檔使用低頻儲存,將縮圖進行標準儲存,獲得了比純低頻更優的最終成本。
和大部分其他廠商技術實現可能存在不同,在vivo雲盤的檔案上傳流程中,有一個非常重要的一環,即檔案的預上傳。
在進行實際檔案二進位制流的上傳之前,雲盤使用者端會讀取檔案的各項屬性,諸如檔名,大小,長寬、照片的拍攝時間等資訊,將這部分資料傳輸給伺服器,我們把這一步叫做預上傳。
而伺服器則會進行使用者剩餘空間大小的邏輯計算,如果剩餘空間不足以存放該檔案,則會直接終止上傳流程。
如果空間足夠,此時伺服器在此時就會扣減使用者空間,然後才會進行下一步的檔案體傳輸。而大部分其他友商只有當檔案完成整個上傳流程時才進行空間扣減。
該邏輯能保證同一個使用者在進行多執行緒上傳,或者多個裝置同時上傳時,不會出現空間超用的情形。
不知道大家平時在使用一些雲盤類似工具的時候有沒有發現,自己明明上傳了一個很大的檔案,但是卻很快就完成了。
那麼這種快速進行檔案上傳的能力,我們這邊就成為"秒傳",形象的釋義就是彷彿在秒級完成了一個大檔案的傳輸。
"秒傳"不僅對使用者體驗有一定的提升,而且也能節省比較可觀的儲存成本。
在vivo雲盤的設計中,秒傳又分為使用者級秒傳和全域性秒傳,分敘如下:
使用者級秒傳:使用者上傳自己之前曾經上傳過的檔案時,觸發秒傳動作。
全域性秒傳:使用者上傳的檔案之前有其他人上傳過,觸發秒傳動作。
秒傳的設計思路較為簡單,使用者進行預上傳時,將檔案摘要告知伺服器,伺服器查詢該摘要值是否已經儲存,若存在就告知使用者端無需進行檔案實體的傳輸。
雲服務使用者的非檔案類資料主要還是儲存在MySQL資料庫裡。海量的資料儲存隨著帶來的是MySQL的硬體成本的提升。當前雲服務MySQL資料庫範例就有將近30+。
為了儘可能降低MySQL的儲存成本,雲服務對MySQL的資料做了相應的資料壓縮。
雲服務採用的是MySQL官方提供的innodb壓縮方案:
雲服務通過線上實踐,對聯絡人資料庫進行壓縮驗證:壓縮之前磁碟佔用空間2.75T,壓縮後空間1.3T,壓縮率可達50%。
說明:壓縮效果取決於表的欄位的型別,典型資料通常具有重複值,因此能夠有效壓縮。CHAR,VARCHAR,TEXT、BLOB這類字串型別的資料通常能夠很好地壓縮。而二進位制資料(整數或浮點數位)、已經經過壓縮的資料(JPEG 或 PNG 影象)通常起不到壓縮效果。
矛盾加密
目前使用者端和伺服器之間的通訊統一通過HTTPS進行傳輸,然而有了HTTPS一定就安全了麼?
考慮以下場景:
使用者端HTTPS的相關校驗均是系統庫實現的,那麼作為攻擊者可以改寫這些系統庫的執行邏輯使得相關校驗「失效」,從而發起「中間人攻擊」
若APK被Hook,也可使得HTTPS的相關校驗失效,從而發起「中間人攻擊」。
所以,為了更高的安全性考慮,我們除了基於HTTPS的檔案傳輸,雲盤在核心介面上還是用了公司內部自研的矛盾SDK加密。
這使得就算HTTPS被諸如中間人代理方式獲取了明文資料後,還是無法對訊息體的敏感資訊進行提取。
檔案儲存安全有兩個重要部分組成:
使用者可以在以後任意時間點存取到儲存在雲端的完整檔案,需要保證檔案的安全儲存永不丟失。
使用者的檔案儲存是私密的,不該有非預期的人或物能非預期的讀取到這些私密檔案。
我們把上述的1稱作為資料的永續性安全,2稱作為資料的隱私安全。
一般來說,第三方公有云提供的物件儲存都能保證11個9的資料永續性,即99.999999999%,開啟異地備份後,能達到12個9,能滿足檔案在儲存上的永續性要求。所以下面我們主要聊下使用者的隱私安全。
早在2019年,就有某大牌手機廠商,其雲端的使用者私人照片竟然全部洩露,個人的隱私照片竟然能在搜尋引擎中查詢到,這個就是典型的使用者私人檔案未被授權即被非法讀取使用。
該事件一旦發生,非常容易被輿論發酵,進而迅速影響企業的口碑,所以,這塊安全方面的設計就顯得重中之重。
儲存加密
我們能通過很多技術手段保證自身服務的足夠安全,但由於使用者檔案最終儲存在公有云的物件儲存中,而各家公有云的技術實現細節我們並不知悉,是否真正具備了足夠高的安全性,我們並不能得知。
所以,我們針對存放在第三方公有云的使用者資料全部進行了加密, 這樣,連儲存方也無法獲取我們使用者的明文件案,我們只需要保證自身業務足夠的安全,而無需關注第三方物件儲存洩露檔案的可能性。
在對檔案的加密時,我們更是使用了最為嚴格的加密手段:每個使用者的每個檔案均使用不同的金鑰進行了加密。這樣即便"駭客"通過某種技術手段拿到了某一個檔案的金鑰,他也無法對大量的其他檔案進行解密。
該方案雖然大大提升了檔案的安全性,但是由於檔案在業務方存在了加密解密動作,除了對效能有一定的損耗,一些媒體能力也受到了限制。比如我們沒法直接使用第三方的內容稽核、圖片處理等服務。
不使用CDN
眾所周知,CDN技術的成熟發展,使得終端使用者可以就近獲取各種網路資源。但是由於CDN的本質是對內容進行了快取,如果我們將使用者的私人檔案通過CDN的方案進行存取,那麼這些檔案被CDN運營商以明文方式快取在了各個邊緣節點上,存在被非法獲取的風險。
和其他網路硬碟形式不同,vivo雲盤主要以存放使用者私人檔案為主,目前並沒有開放檔案的傳播分享行為。在這種業務場景下,使用CDN的效率並不高,快取的資源並不會被多次重複利用。所以vivo雲服務不會對使用者的私人檔案使用CDN技術以提升效能。
令牌有效期設計
雲盤的檔案以連結的方式暴露給各使用者端進行下載。在連結的設計上,雲盤攜帶了下載令牌,該令牌在一定有效期內會自動過期。
vivo雲服務的使用者量級目前還在持續增加,從使用者體驗方面著想,目前雲服務的功能完備性還可以有不少發掘的點,未來我們還將構築以下能力:
離線下載能力:使用者可以使用雲端的下載功能將檔案儲存到使用者的雲盤中。
檔案協同編輯:隨著vivo pad產品的釋出,後續使用者可以在不同端基於雲服務完成檔案的協同編輯。
無縫換機體驗:推動手機100+資料項接入,為使用者打造無縫的換機體驗。