Spring Cloud Alibaba | Sentinel:分佈式系統的流量防衛兵基礎實戰

Spring Cloud Alibaba | Sentinel:分佈式系統的流量防衛兵基礎實戰

Springboot: 2.1.8.RELEASEjava

SpringCloud: Greenwich.SR2git

1. Sentinel控制檯概述

在介紹入門實戰以前,先來介紹一下Sentinel。Sentinel控制檯提供一個輕量級的開源控制檯,它提供機器發現以及健康狀況管理、監控(單機和集羣),規則管理和推送的功能。github

Sentinel控制檯主要功能:web

  • 查看機器列表以及健康狀況:收集 Sentinel 客戶端發送的心跳包,用於判斷機器是否在線。
  • 監控 (單機和集羣聚合):經過 Sentinel 客戶端暴露的監控 API,按期拉取而且聚合應用監控信息,最終能夠實現秒級的實時監控。
  • 規則管理和推送:統一管理推送規則。
  • 鑑權:生產環境中鑑權很是重要,每一個用戶都須要相應的權限能夠對控制檯的信息進行修改。

2. Sentinel控制檯部署:

Sentinel控制檯部署有兩種方案:spring

2.1 下載

直接使用官方編譯好的Release版本部署啓動,下載地址:https://github.com/alibaba/Sentinel/releases ,目前最新版本是v1.6.3,下載sentinel-dashboard-1.6.3.jar,如圖:瀏覽器

2.2 啓動

可使用最新版本的源碼自行構建Sentinel控制檯,首先須要下載控制檯工程,下載路徑:https://github.com/alibaba/Sentinel/tree/master/sentinel-dashboard ,使用命令mvn clean package將代碼打成jar包便可。session

在CentOS中使用以下命令啓動Sentinel控制檯工程:mvc

注意:啓動 Sentinel 控制檯須要 JDK 版本爲 1.8 及以上版本。app

nohup java -Dserver.port=8080 -Dcsp.sentinel.dashboard.server=localhost:8080 -Dproject.name=sentinel-dashboard -jar sentinel-dashboard-1.6.3.jar >sentinel-dashboard.out 2>&1 &

-Dserver.port=8080 用於指定 Sentinel 控制檯端口爲 8080。啓動完成後,使用瀏覽器訪問:http://ip:8080/ ,這時會進入登陸頁面,從 Sentinel 1.6.0 起,Sentinel 控制檯引入基本的登陸功能,默認用戶名和密碼都是sentinel,如圖:分佈式

Sentinel Dashboard能夠經過以下參數進行配置:

  • -Dsentinel.dashboard.auth.username=sentinel 用於指定控制檯的登陸用戶名爲 sentinel;
  • -Dsentinel.dashboard.auth.password=123456 用於指定控制檯的登陸密碼爲 123456;若是省略這兩個參數,默認用戶和密碼均爲 sentinel;
  • -Dserver.servlet.session.timeout=7200 用於指定 Spring Boot 服務端 session 的過時時間,如 7200 表示 7200 秒;60m 表示 60 分鐘,默認爲 30 分鐘;

一樣也能夠直接在Spring的application.properties文件中進行配置。

3. Spring Cloud

Sentinel目前已支持Spring Cloud,須要引入spring-boot-starter-web來觸發sentinel-starter中相關的自動配置。

3.1 建立父工程sentinel-springcloud

工程依賴pom.xml以下:

代碼清單:Alibaba/sentinel-springcloud/pom.xml
***

<dependencyManagement>
    <dependencies>
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-dependencies</artifactId>
            <version>${spring-cloud.version}</version>
            <type>pom</type>
            <scope>import</scope>
        </dependency>
        <dependency>
            <groupId>com.alibaba.cloud</groupId>
            <artifactId>spring-cloud-alibaba-dependencies</artifactId>
            <version>${spring-cloud-alibaba.version}</version>
            <type>pom</type>
            <scope>import</scope>
        </dependency>
    </dependencies>
</dependencyManagement>

<dependencies>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-actuator</artifactId>
    </dependency>
    <dependency>
        <groupId>com.alibaba.cloud</groupId>
        <artifactId>spring-cloud-starter-alibaba-sentinel</artifactId>
    </dependency>

    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-test</artifactId>
        <scope>test</scope>
    </dependency>
</dependencies>

spring-cloud-alibaba-dependencies引入Spring Cloud Alibaba版本控制。spring-cloud-starter-alibaba-sentinel引入Sentinel組件。

3.2 建立子工程web_mvc:

工程依賴pom.xml以下:

代碼清單:Alibaba/sentinel-springcloud/web_mvc/pom.xml
***

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-web</artifactId>
</dependency>

工程配置application.yml以下:

代碼清單:Alibaba/sentinel-springcloud/web_mvc/src/main/resources/application.yml
***

server:
  port: 8000
spring:
  application:
    name: web-mvc
  cloud:
    sentinel:
      transport:
        dashboard: 192.168.44.129:8080
        port: 8719
  • spring.cloud.sentinel.transport.dashboard:配置Sentinel控制檯的ip和端口
  • spring.cloud.sentinel.transport.port:這個端口配置會在應用對應的機器上啓動一個 Http Server,該 Server 會與 Sentinel 控制檯作交互。好比 Sentinel 控制檯添加了1個限流規則,會把規則數據 push 給這個 Http Server 接收,Http Server 再將規則註冊到 Sentinel 中。

建立測試接口HelloController.java以下:

代碼清單:Alibaba/sentinel-springcloud/web_mvc/src/main/java/com/springcloud/web_mvc/controller/HelloController.java
***

@RestController
public class HelloController {

    @GetMapping(value = "/hello")
    @SentinelResource("hello")
    public String hello() {
        return "Hello Web MVC";
    }
}

@SentinelResource註解用來標識資源是否被限流、降級。上述例子上該註解的屬性 'hello' 表示資源名。該註解還有一些其餘更精細化的配置,好比忽略某些異常的配置、默認降級函數等等,具體可見以下說明:

  • value:資源名稱,必需項(不能爲空)
  • entryType:entry 類型,可選項(默認爲 EntryType.OUT)
  • blockHandler / blockHandlerClass: blockHandler 對應處理 BlockException 的函數名稱,可選項。blockHandler 函數訪問範圍須要是 public,返回類型須要與原方法相匹配,參數類型須要和原方法相匹配而且最後加一個額外的參數,類型爲 BlockException。blockHandler 函數默認須要和原方法在同一個類中。若但願使用其餘類的函數,則能夠指定 blockHandlerClass 爲對應的類的 Class 對象,注意對應的函數必需爲 static 函數,不然沒法解析。
  • fallback:fallback 函數名稱,可選項,用於在拋出異常的時候提供 fallback 處理邏輯。fallback 函數能夠針對全部類型的異常(除了 exceptionsToIgnore 裏面排除掉的異常類型)進行處理。fallback 函數簽名和位置要求:
    • 返回值類型必須與原函數返回值類型一致;
    • 方法參數列表須要和原函數一致,或者能夠額外多一個 Throwable 類型的參數用於接收對應的異常。
    • fallback 函數默認須要和原方法在同一個類中。若但願使用其餘類的函數,則能夠指定 fallbackClass 爲對應的類的 Class 對象,注意對應的函數必需爲 static 函數,不然沒法解析。
  • defaultFallback(since 1.6.0):默認的 fallback 函數名稱,可選項,一般用於通用的 fallback 邏輯(便可以用於不少服務或方法)。默認 fallback 函數能夠針對全部類型的異常(除了 exceptionsToIgnore 裏面排除掉的異常類型)進行處理。若同時配置了 fallback 和 defaultFallback,則只有 fallback 會生效。defaultFallback 函數簽名要求:
    • 返回值類型必須與原函數返回值類型一致;
    • 方法參數列表須要爲空,或者能夠額外多一個 Throwable 類型的參數用於接收對應的異常。
    • defaultFallback 函數默認須要和原方法在同一個類中。若但願使用其餘類的函數,則能夠指定 fallbackClass 爲對應的類的 Class 對象,注意對應的函數必需爲 static 函數,不然沒法解析。
  • exceptionsToIgnore(since 1.6.0):用於指定哪些異常被排除掉,不會計入異常統計中,也不會進入 fallback 邏輯中,而是會原樣拋出。

注:1.6.0 以前的版本 fallback 函數只針對降級異常(DegradeException)進行處理,不能針對業務異常進行處理。

特別地,若 blockHandler 和 fallback 都進行了配置,則被限流降級而拋出 BlockException 時只會進入 blockHandler 處理邏輯。若未配置 blockHandler、fallback 和 defaultFallback,則被限流降級時會將 BlockException 直接拋出。

3.3 測試

啓動子工程web_mvc,啓動成功後打開瀏覽器訪問:http://localhost:8000/hello ,能夠看到頁面正常顯示Hello Web MVC,屢次刷新後打開Sentinel Dashboard,在Sentinel控制檯上已經能夠看到咱們的web-mvc應用了,如圖:

  • 注意:請確保客戶端有訪問量,Sentinel 會在客戶端首次調用的時候進行初始化,開始向控制檯發送心跳包。

4. Spring WebFlux

Sentinel目前已經支持WebFlux,須要配合spring-boot-starter-webflux依賴觸發 sentinel-starter中WebFlux相關的自動化配置。具體接入方式以下:

4.1 建立子工程web_flux

工程依賴pom.xml以下:

代碼清單:Alibaba/sentinel-springcloud/web_flux/pom.xml
***

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-webflux</artifactId>
</dependency>

spring-boot-starter-webflux引入WebFlux的相關依賴,Sentinel的依賴已在父工程引入。

4.2 配置文件application.yml以下:

代碼清單:Alibaba/sentinel-springcloud/web_flux/src/main/resources/application.yml


server:
  port: 9000
spring:
  application:
    name: web-flux
  cloud:
    sentinel:
      transport:
        dashboard: 192.168.44.129:8080
        port: 8720

4.3 測試接口HelloController.java

代碼清單:Alibaba/sentinel-springcloud/web_flux/src/main/java/com/springcloud/web_flux/controller/HelloController.java
***

@RestController
public class HelloController {

    @GetMapping("/hello")
    @SentinelResource("hello")
    public Mono<String> mono() {
        return Mono.just("Hello Web Flux")
                .transform(new SentinelReactorTransformer<>("resourceName"));
    }
}

4.4 測試

啓動子工程web_flux,打開瀏覽器訪問:http://localhost:9000/hello ,頁面正常顯示Hello Web Flux,屢次刷新頁面後打開Sentinel控制檯,能夠看到web_flux工程正常註冊,測試成功,如圖:

5. 示例代碼

Github-示例代碼

Gitee-示例代碼

相關文章
相關標籤/搜索