抓 Bug 神器的工作原理——聊聊 Sentry 的架構

Sentry 是什麼?這是一個用於錯誤上報的服務中心,使用近乎一致的 API 設計,統一了不同語言生產環境代碼異常上報的難題。

2020 年二月份,領導讓我負責在公司內部測試和使用 Sentry,彼時 Sentry 的文檔還不是很完善,我也只是初步接觸基礎服務的搭建,Sentry 於我而言就是一個黑盒子

2016 年,Sentry 的開發者答覆說目前沒有任何關於 Sentry 架構的公開資料,最佳的途徑就是閱讀源碼:)這個工程量確實比較大,我個人在使用 Docker-compose 搭建 Sentry 時,借用一連串的日誌輸出來觀察整個數據流,根據服務間的依賴也只能猜測大致的架構。

2020 年下半年,Sentry 開始陸續將文檔補全,這個項目的架構圖終被公開,結合其他文檔,Sentry 的數據流浮出水面。

架構概述

下方這個圖是根據 Sentry 官方文檔重繪的,我把所有存儲相關的組件用紫色的圖形做了區分,其他 Sentry 服務組件用藍色表示(除了頂部的應用)。

這樣畫下來之後,服務基本就分層完畢:

  1. Loadbalancer(負載均衡器)負責路由轉發(這一服務由用戶搭建),錯誤上報轉發到 /api/\d+/store ,其他項目、成員、錯誤管理功能由 Sentry Web 負責。這一層的承擔數據入口、展示的作用
  2. Relay 負責消息中繼轉發,並把數據先彙集到 Kafka;Snuba 負責接收 SentryWeb 的請求,進行數據的聚合、搜索;Sentry Worker 則是一個隊列服務,主要負責數據的存儲。
  3. Kafka 作爲消息隊列,ClickHouse 負責接近實時的數據分析,Redis(主要) 和 Memcached 負責項目配置、錯誤基礎信息的存儲和統計。Postgres 承擔基礎數據持久化(主要是項目、用戶權限管理等)Symbolicator 主要用於錯誤信息格式化。
  4. 最底下的 Zookeeper 是 Kafka 用於節點信息同步的,如果我們設置了多個 ClickHouse 節點,也可以用它來保存主從同步信息或者做分佈式表。

Relay —— 錯誤信息處理的中轉站

Relay 收到原始數據後,主要做這幾件事。

  1. 對其格式進行有效性校驗
  2. 查詢內存或者從 Redis 拉取緩存得到項目配置信息,校驗請求是否合法(項目是否存在或者有沒有觸發限流,沒觸發限流則會對 API 額度進行累計,寫入 Redis)
  3. 發起一個異步請求給定時任務(SentryWorker,postprocess-event)做下一步處理

Kafka 和 Celery —— 應用解耦和異步保存數據

Relay 數據轉發到 Kafka 的 ingest-events Topic(Ingest 即攝取),消費者消費後把消息放入 postprocess-event 這個 Celery 定時任務服務排隊處理。隊列做的事情如下

  1. Symbolicate-event,在 iOS 上有個叫 symbolicate-crash 的工具,是將機器的崩潰日誌轉化爲可讀的崩潰代碼定位日誌,這裏的 Symbolicator 同樣承擔類似的職能,由它經手的消息,我們就可以在頁面上看到代碼在哪裏出錯了。
  2. process-event,字面含義就是處理消息,在 Sentry 上啓用的插件(Plugins or Integration)會在這個步驟中應用到消息體上,例如,整合了一個 Slack bot(機器人),就會在這個步驟發送告警。
  3. save-event,消息經過簡化,保存到數據庫,同時再次發到 Kafka,但這次換到 event Topic,Snuba 這個搜索組件內部會有一個消費者,對這部分數據批量寫入到 ClickHouse。你可能好奇爲什麼不直接存進去算了還要搞多這一步,這是因爲 ClickHouse 雖然大數據量處理能力很強,但頻繁寫入能力是真的菜雞(假設做了主從,那就更災難了,把從庫和 Zookeeper 都一起拉下水),所以需要 Snuba 來限制寫入頻率

Sentry Web


Sentry Web 這邊主要跟配置等持久化數據打交道,創建項目、權限控制、限流分配等都是它負責。查詢搜索錯誤消息、Dashboard 聚合等功能則是 Snuba 承擔,由它來當翻譯官,把用戶查詢條件轉化爲 SQL 語句發給 ClickHouse。

題外話 —— 爲什麼 Sentry 適合商用

以往的開源項目大部分可以看成是單個組件,升級修復的工作量對一般的工程師而言還是可以接受的。但是 Sentry 這個錯誤上報服務背後卻是十幾二十個微服務組成的,一次服務升級可能涉及到很多個微服務、存儲服務,瞬間依賴爆炸,測試無從下手

對於小公司而言,如果不使用 Docker,搭建一個 Sentry 服務,就需要很多臺服務器,如果要做主從、集羣還需要再乘以 N,如果要做 TLS,又得花大筆錢去購置證書。本來是想節省代碼查錯的時間成本,可能最後卻多花了錢在部署和運維上。

單租戶隔離(Single Tenant Isolation)、持續集成測試、TLS 加密、容災都交給了 Sentry 來做,給它打錢自然而然地成了最划算的方案,不得不說,真羨慕這種站着賺錢的項目:)

參考資料

  1. [Question] Sentry Architecture #3419
  2. Path of an Event through Relay
  3. Sentry: Event Ingestion Pipeline
  4. Introducing Snuba: Sentry's New Search Infrastructure
  5. The Architecture Of Sentry
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章