為什么實時分析既需要NoSQL的靈活性,又需要SQL系統的嚴格模式?
?作為地球上最堅硬的物質,鉆石的用途令人驚訝地有限:鋸片、鉆頭、結婚戒指和其他工業應用。
相比之下,自然界中較軟的金屬之一--鐵,可以被改造成無盡的應用:最鋒利的刀片、最高的摩天大樓、最先進的汽車, 巨大的輪船,而且很快,如果埃隆-馬斯克是對的,就會有最有效的電動車電池。
換句話說,鐵之所以有令人難以置信的用處,是因為它既是剛性的又是柔性的。
同樣,數據庫只有在既嚴格又靈活的情況下才對今天的實時分析有用。
傳統的數據庫,由于其完全靈活的結構,是很脆的。無模式的NoSQL數據庫也是如此,它們能夠攝取大量的數據,但在從這些數據中提取復雜的見解方面卻很差。
用戶個性化,自動庫存管理,智能運維和其他實時用例要求數據庫嚴格執行模式,并擁有根據數據本身自動重新定義這些模式的靈活性。這滿足了現代分析的三個關鍵要求:
- 支持采集數據的規模和速度
- 支持靈活的模式,可以立即適應流式數據的多樣性
- 支持快速、復雜的SQL查詢,需要嚴格的結構或模式
昨天的模式:堅硬而脆弱
經典的模式是關系型數據庫表:實體的行,例如人,以及這些實體的不同屬性(年齡或性別)的列。通常存儲在SQL語句中,模式還定義了數據庫中所有的表以及它們之間的關系。
傳統上,模式是嚴格執行的。不符合預定屬性或數據類型的輸入數據會被數據庫自動拒絕,在其位置上存儲一個空值或完全跳過整個記錄。改變模式是很困難的,也是很少做的。公司小心翼翼地設計他們的ETL數據管道,以便與他們的模式保持一致(反之亦然)。
在過去,預先創建和嚴格執行模式有很好的理由。SQL查詢更容易編寫。它們的運行速度也快了很多。最重要的是,嚴格的模式可以防止由不良或不匹配的數據造成的查詢錯誤。
然而,嚴格的、一成不變的模式在今天有著巨大的弊端。首先,現在的數據來源和類型比90年代多得多。他們中的許多人不能輕易地適應相同的模式結構。最值得注意的是實時事件流。流媒體和時間序列數據通常以經常變化的半結構化格式到達。隨著這些格式的改變,模式也必須改變。
其次,隨著業務條件的變化,公司不斷需要分析新的數據源,運行不同類型的分析--或者簡單地更新其數據類型或標簽。
這里有一個例子。當我在Fackbook的數據基礎設施團隊的時候,我們參與了一項雄心勃勃的計劃,名為"花蜜項目 "的用戶群正在爆炸性增長。"花蜜項目 "試圖用一套標準的屬性來記錄每個用戶的行為。在全球范圍內實現這一模式的標準化,將使我們能夠在全球范圍內分析趨勢并發現異常情況。經過許多內部辯論,我們的團隊同意在Hadoop中使用一個名為time_spent的列中的時間戳來存儲每個用戶事件,該列的分辨率為一秒。
在 "花蜜項目 "首次亮相后,我們向一組新的應用程序開發人員展示了它。他們問的第一個問題是"你能把列的花費時間從秒改為毫秒嗎?"換句話說,他們隨口要求我們在Nectar項目推出后重建其模式的一個基本方面。
ETL管道可以使你所有的數據源都在同一個傳說中的屋頂下(這就是T,代表數據轉換的意思)。然而,ETL管道的設置、操作以及隨著數據來源和類型的變化而進行的手動更新都很耗時和昂貴。
靈活性的嘗試
嚴格的、一成不變的模式破壞了靈活性,而今天所有的公司都需要這種靈活性。一些數據庫制造商通過使用戶更容易手動修改他們的模式來應對這個問題。不過,這也是一個沉重的代價。
使用SQL ALTER-TABLE命令改變模式需要大量的時間和處理能力,使你的數據庫長時間處于離線狀態。而且,一旦模式被更新,就很有可能在無意中破壞你的數據,使你的數據管道癱瘓。
以 PostgreSQL,是流行的交易型數據庫,許多公司也用它來做簡單的分析。為了正確攝取當今快速變化的事件流,PostgreSQL必須通過SQL中的手動ALTER-TABLE命令來改變其模式。這將鎖定數據庫表,并在ALTER-TABLE完成的時間內凍結所有查詢和交易。據說,無論你的PostgreSQL表有多大,ALTER-TABLE都需要很長的時間。它還需要大量的CPU,并造成數據錯誤和下游應用中斷的風險。
NewSQL數據庫也面臨同樣的問題。 CockroachDB 承諾在線改變Schema具有零停機時間。然而,Cockroach警告說不要一次做超過一個模式的改變。它也強烈警告不要在交易中改變模式。就像PostgreSQL一樣,CockroachDB的所有模式改變都必須由用戶手動完成。因此,CockroachDB的模式遠沒有表面上那么靈活。而且,數據錯誤和數據停機的風險也同樣存在。
NoSQL來拯救?
其他制造商發布的NoSQL數據庫大大放松了模式,或者完全放棄了模式。
這種激進的設計選擇使NoSQL數據庫--文檔數據庫、鍵值存儲、面向列的數據庫和圖形數據庫--非常適合將各種類型的海量數據存儲在一起,無論是結構化、半結構化還是多態化的數據。
Data lakes建立在NoSQL數據庫(如Hadoop)上的數據湖是混合類型的擴展數據存儲庫的最好例子。NoSQL數據庫在檢索大量數據和運行簡單查詢方面也很迅速。
然而,輕量級/非輕量級模式數據庫確實存在弊端。
雖然查找和簡單的查詢可以是快速和簡單的,但復雜的嵌套的和必須返回精確答案的查詢往往運行緩慢,而且難以創建。這是由于缺乏SQL支持,以及他們傾向于對索引和其他查詢優化的支持不力。復雜的查詢甚至更有可能超時而不返回結果,這是因為NoSQL的過于寬松的數據一致性模型。修復和重新運行查詢是一件浪費時間的麻煩事。而當涉及到云計算和開發人員時,這意味著浪費金錢。
以作為Hadoop堆棧一部分的Hive分析數據庫為例。Hive確實支持靈活的模式,但很粗略。當它遇到不適合整齊地放入現有表格和數據庫的半結構化數據時,它只是將數據存儲為一個 JSON-like blob,這可以保持數據的完整性。然而,在查詢時,Blobs需要首先被反序列化,這是一個緩慢而低效的過程。
或者采取亞馬遜DynamoDB為例,它使用的是無模式的鍵值存儲。DynamoDB在讀取特定記錄時速度超快。多記錄查詢往往要慢得多,盡管建立二級索引可以幫助。更大的問題是,DynamoDB不支持任何JOIN或任何其他復雜查詢。
嚴格和靈活模式的正確方法
然而,有一個成功的數據庫公式,它融合了NoSQL的靈活可擴展性和SQL的準確性和可靠性,同時又加入了云原生基礎設施的低操作簡單性。
Rockset是一個建立在RocksDB鍵值存儲之上的實時分析平臺。像其他NoSQL數據庫一樣,Rockset具有高度的可擴展性、靈活性和快速寫入數據的能力。但與SQL關系型數據庫一樣,Rockset也有嚴格的模式優勢。強數據類型和高度的數據一致性,再加上我們的自動和高效的 Converged Indexing這些優勢與我們的自動和高效的數據庫相結合,確保你的復雜的SQL查詢是快速的。
Rockset自動生成Schema通過檢查數據的字段和數據類型,因為它是存儲的。而且Rockset可以處理扔給它的任何類型的數據,包括。
- 具有深度嵌套數組和對象的JSON數據,以及混合數據類型和稀疏字段
- 實時事件流,隨著時間的推移不斷增加新的字段
- 來自新數據源的新數據類型
支持無模式攝入和融合索引,使Rockset能夠通過消除對上游數據轉換的需求來減少數據延遲。
Rockset還有其他優化功能,以減少存儲成本和加速查詢。對于每條記錄的每一個字段,Rockset都會存儲數據類型。這最大限度地提高了查詢性能和減少了錯誤。而且,我們通過一個叫做字段互換的功能有效地做到了這一點,與無模式的基于JSON的文檔數據庫相比,例如,所需的存儲量最多可減少30%。
Rockset使用了一種叫做類型提升的東西來減少查詢的處理時間。具有相同類型的相鄰項目可以將其類型信息提升到適用于整個項目集,而不是存儲在列表中的每一個單獨的項目。這使得矢量的CPU指令能夠快速處理整個項目集。這個實現--連同我們的 Converged Index?--使Rockset查詢能夠像具有剛性模式的數據庫一樣快速運行,而不會產生額外的計算。
一些NoSQL數據庫的制造商聲稱只有他們能支持靈活的模式。 這不是真的,而且是Rockset等現代產品正在打破的一個神話。?