微服務框架核心源碼深度解析<<大廠學院完結>>


Sentinel核心源碼解析

Sentinel是分布式系統的防御系統。以流量為切入點,通過動態設置的流量控制、服務熔斷等手段達到

保護系統的目的,通過服務降級增強服務被拒后用戶的體驗。

一、Sentinel工作原理

1 架構圖解析

若要讀懂Sentinel源碼,則必須要搞明白官方給出的Sentinel的架構圖。

微服務框架核心源碼深度解析<<大廠學院完結>>

Sentinel的核心骨架是ProcessorSlotChain。其將不同的 Slot 按照順序串在一起(責任鏈模式),從而將不同的功能組合在一起(限流、降級、系統保護)。系統會為每個資源創建一套SlotChain。

2 SPI機制

Sentinel槽鏈中各Slot的執行順序是固定好的。但並不是絕對不能改變的。Sentinel將ProcessorSlot 作為 SPI 接口進行擴展,使得 SlotChain 具備了擴展能力。用戶可以自定義Slot並編排Slot 間的順序。

3 Slot簡介

NodeSelectorSlot

負責收集資源的路徑,並將這些資源的調用路徑,以樹狀結構存儲起來,用於根據調用路徑來限流降。

ClusterBuilderSlot

用於存儲資源的統計信息以及調用者信息,例如該資源的 RT, QPS, thread count,Block count,Exception count 等等,這些信息將用作為多維度限流,降級的依據。簡單來說,就是用於構建ClusterNode。

StatisticSlot

用於記錄、統計不同緯度的 runtime 指標監控信息。

ParamFlowSlot

對應熱點流控。

FlowSlot

用於根據預設的限流規則以及前面 slot 統計的狀態,來進行流量控制。對應流控規則。

AuthoritySlot

根據配置的黑白名單和調用來源信息,來做黑白名單控制。對應授權規則。

DegradeSlot

通過統計信息以及預設的規則,來做熔斷降級。對應降級規則。

SystemSlot

通過系統的狀態,例如 load1 等,來控制總的入口流量。對應系統規則。

4 Context簡介

Context是對資源操作的上下文,每個資源操作必須屬於一個Context。如果代碼中沒有指定Context,則會創建一個name為sentinel_default_context的默認Context。一個Context生命周期中可以包含多個資源操作。Context生命周期中的最后一個資源在exit()時會清理該Conetxt,這也就意味着這個Context生命周期結束了。

5 Context代碼

// 創建一個來自於appA訪問的Context,
// entranceOne為Context的name
ContextUtil.enter("entranceOne", "appA");
// Entry就是一個資源操作對象
Entry resource1 = null;
Entry resource2 = null;
try {
// 獲取資源resource1的entry
resource1 = SphU.entry("resource1");
// 代碼能走到這里,說明當前對資源resource1的請求通過了流控
// 對資源resource1的相關業務處理。。。
// 獲取資源resource2的entry
resource2 = SphU.entry("resource2");
// 代碼能走到這里,說明當前對資源resource2的請求通過了流控
// 對資源resource2的相關業務處理。。。
} catch (BlockException e) {
// 代碼能走到這里,說明請求被限流,
// 這里執行降級處理
} finally {
if (resource1 != null) {
resource1.exit();
}
if (resource2 != null) {
resource2.exit();
}
}
// 釋放Context
ContextUtil.exit();
// --------------------------------------------------------

  

 

// 創建另一個來自於appA訪問的Context,
// entranceTwo為Context的name
ContextUtil.enter("entranceTwo", "appA");
// Entry就是一個資源操作對象
Entry resource3 = null;
try {
// 獲取資源resource2的entry
resource2 = SphU.entry("resource2");
// 代碼能走到這里,說明當前對資源resource2的請求通過了流控
// 對資源resource2的相關業務處理。。。
// 獲取資源resource3的entry
resource3 = SphU.entry("resource3");
// 代碼能走到這里,說明當前對資源resource3的請求通過了流控
// 對資源resource3的相關業務處理。。。
} catch (BlockException e) {
// 代碼能走到這里,說明請求被限流,
// 這里執行降級處理
} finally {
if (resource2 != null) {
resource2.exit();
}
if (resource3 != null) {
resource3.exit();
}
}
// 釋放Context
ContextUtil.exit();

  

6 Node間的

Node:用於完成數據統計的接口

StatisticNode:統計節點,是Node接口的實現類,用於完成數據統計

EntranceNode:入口節點,一個Context會有一個入口節點,用於統計當前

Context的總體流量數據

DefaultNode:默認節點,用於統計一個資源在當前Context中的流量數據

ClusterNode:集群節點,用於統計一個資源在所有Context中的總體流量

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM