淺談Observability

·

2 min read

Observability的歷史

(又在講古了XD) Observability這詞, 最早在控制理論出現, 這是一門關注如何控制動態系統的工程學科, 其中的Rudolf E. Kálmán在1960的論文中提出的.

Observability to describe mathematical control systems. In control theory, observability is defined as a measure of how well internal states of a system can be inferred from knowledge of its external outputs.

恩...大概就根據一個系統的外部輸出的資訊來推斷內部狀態的能力,甚至可以透過輸出的資訊搭配知識來做出推斷假設與證明. 進而優化再持續性的觀測, 是不能稱為系統具備可觀測性的, 因為這樣子組織會高度依賴少部份人的能力而帶來管理風險.

https://ithelp.ithome.com.tw/upload/images/20220904/20104930NtEuKNpTjR.png

這也呼應了DevOps的8字環.

Kálmán後來有把這論文的理論, 用在軟體系統上, 並且給出了更詳細的要求, 只有滿足了才可稱為具備Observability.

  1. 了解應用程式的內部運作

  2. 了解你的應用程式可以進入任何的系統狀態, 甚至你以前都沒見過也無法預測的新狀態

  3. 僅透過觀察與存取外部工具來了解軟體的內部運作與系統狀態

  4. 了解內部狀態, 不需要提供任何新的自定義程式來處理解析它.

Observability Engineering這本書的第一章, 有提出很多小問題來詢問自己是否夠了解自己的系統. 我隨便舉兩三題 1.是否曾經遇過線上問題, 自己都能解釋異常狀況, 沒碰到過排查的死胡同, 最後只能靠通靈跟重開機. 2.如果有用戶抱怨系統很慢, 但你的監控面板顯示99th, 99.9th甚至99.99th的請求都很快, 能找到隱藏的超時嘛?

之類的很多問題XD

1988年, SNMPv1定義在RFC1157, 其中提到了大家很熟悉的Monitoring. 其中有Metric度量指標,它是一個數字, 跟隨著一些tag, 我們就能用這些tag對這些metrics的數字做一些分類和搜尋. 通常這些metric指標都是一次性產生、廉價的存儲空間. 但它們又通常會用Time-Series bucket(時間序列集合)來聚合存放. 現在有很多複雜的應用或組織運作都建立在Metric指標上, 像是Time-Series databases(TSDBs)、一些統計分析、圖形儀表板、運維團隊、On-Call輪轉等等的, 很多方式能展示跟告知團隊. 但這些總有上限, 這上限在這些metric指標都是自己對系統已知的資訊. 平常跑得很正常的系統, 突然壞了, metric指標也不出來時, 大部分的運維團隊就會用low-level的指令來查找問題, 像是strace, tcpdump等等數百條命令來嘗試讓主機來回答問題.

且現在的系統架構往往是

  1. 一個應用系統有多組服務來支撐, 換言之系統很複雜

  2. 有很多種的持久化服務(像是DB, storage systems)

  3. Infrastructure是很動態地, 像容量就任意的伸縮

  4. 許多服務是我們有依賴, 但不歸屬我們做管理控制

  5. 分散式系統是難以被完整預測的

還有很多原因, 將導致團隊在治理跟排查上遭遇很大的困難. 若是沒有一個高維度(Dimensionality)和高基數(Cardinality)資料, 貫穿在眾多線索中, 將會非常難在現在這樣複雜的系統架構裡快速地找到問題, 甚至證明假設.

基數Cardinality

在關聯式資料庫裡, Cardinality指的是資料的唯一性. Low-cardinality表示一列有很多重複的值. 性別/姓名都算是低基數. High-cardinality意味著該列包含很大比例的唯一值. 所以像UniqueID, UUID這樣的值在該列則能稱為高基數.

Cardinality對於Observability是非常重要的, 因為高基數的資料在Debug或了解系統的資料識別上是最有用有效的. 像是UserIDs, ShoppingCartIDs, RequestIDs其他等等的高基數ID. 又或是我們之後要介紹的TraceIDs, SpanIDs, 或是容器ID, 主機名稱都是查詢唯一ID的好方法. 高基數資料的好處除了方便識別外, 也能轉化成低基數的資料, 像是分類分堆, 資料前綴/後綴等等的; 但低基數的資料卻不能反過來轉化成高基數的資料.

但是!! 大部分基於Metrics的工具或服務(像Prometheus), 基本都是處理低基數的資料. 通常低基數的資料都是要是前先決定好的. 但通常很多人事先不太清楚哪些指標做度量的, 或哪些標籤是需要做識別.

維度Dimensionality

基數講的是資料的唯一性. 維度講的是該資料所擁有key(屬性)的數量. 在Observability System中, Telemetry(遙測)數據是由任意寬度(Wide)的結構化事件所生成的. 這些事件能被稱為Wide, 是因為它們可以包含上百甚至上千個Key-value pair(或者叫維度Dimensionality).

圖上的P是特徵, n則是metric資料. 盡可能描述多點特徵. 統計學對於高維度資料有嚴格的定義[^1].

像之後要介紹的Prometheus, 其metric資料裡面能含有任意數量的k-v pairs; 結構化Log其內容也是有很多k-v pair來描述其上下文的資訊, 便於觀察了解系統.

上下文Context

所有的Signal(之後會解釋), 都有相同的內容. 其實就是在空間上建立資料之間的關聯.

舉例, Prometheus[^2]首頁就有這段描述

https://prometheus.io/

Prometheus就是實現能提供一個高維度資料的模型, 其中也包含了一組任意數量的k-v pair.

在現在這年代, 硬碟容量是很方便被擴充的, 且讀寫速度也遠快於以前. 沒必要省成這樣. 多冗餘些資訊在資料內反而方便之後關聯查詢用. 數據的維度越高, 就越有可能找到系統行為中隱藏或難以捉摸的模式(還是交給數據分析專家幫忙分析好了).

假設我們定義了6個高基數維度的事件, time, app, host, user, endpoint還有status. 我們就可以建立查詢方法來分析這些維度的組合和顯示相關性. 像是可以搜尋所有status是502, time發生在過去半小時內的, 且host是ithome的數據. 或是找所有status是403, 由user是Nathan對著ironman14th這endpoint發生的錯誤, 等等的.

今日小總結

Observability相關的工具或服務, 其實不只是上面提到的metrics, 或者是限制遙測資料的基數跟維度. 反而是鼓勵開發團隊為每個可能發生的事件收集豐富的遙測資訊. 將請求的完整上下文也存儲起來, 在某些時候使用或者分析用.

聊到現在, 感覺上Observability就只是Monitoring換了一層包裝的講法, 但不管如何, Observability都是為了給系統帶來更好的Visibility(可見性), 易於Debugging調試, 是一個穩定的系統在維護與發展上的基石.

明天也會繼續講更多Observability. 謝謝各位與隊友們.

參考資料

[^1]: What is High Dimensional Data? [^2]: Prometheus Observability Whitepaper