ChaosBlade混沌測試實踐

lldhsds發表於2024-05-31

! https://zhuanlan.zhihu.com/p/700914220

ChaosBlade: 一個簡單易用且功能強大的混沌實驗實施工具

官方倉庫:https://github.com/chaosblade-io/chaosblade

1. 專案介紹

ChaosBlade 是阿里巴巴開源的一款遵循混沌工程原理和混沌實驗模型的實驗注入工具,幫助企業提升分散式系統的容錯能力,並且在企業上雲或往雲原生系統遷移過程中業務連續性保障。

Chaosblade 是內部 MonkeyKing 對外開源的專案,其建立在阿里巴巴近十年故障測試和演練實踐基礎上,結合了集團各業務的最佳創意和實踐。

ChaosBlade 不僅使用簡單,而且支援豐富的實驗場景,場景包括:

  • 基礎資源:比如 CPU、記憶體、網路、磁碟、程序等實驗場景;
  • Java 應用:比如資料庫、快取、訊息、JVM 本身、微服務等,還可以指定任意類方法注入各種複雜的實驗場景;
  • C++ 應用:比如指定任意方法或某行程式碼注入延遲、變數和返回值篡改等實驗場景;
  • Docker 容器:比如殺容器、容器內 CPU、記憶體、網路、磁碟、程序等實驗場景;
  • 雲原生平臺:比如 Kubernetes 平臺節點上 CPU、記憶體、網路、磁碟、程序實驗場景,Pod 網路和 Pod 本身實驗場景如殺 Pod,容器的實驗場景如上述的 Docker 容器實驗場景;

將場景按領域實現封裝成一個個單獨的專案,不僅可以使領域內場景標準化實現,而且非常方便場景水平和垂直擴充套件,透過遵循混沌實驗模型,實現 chaosblade cli 統一呼叫。目前包含的專案如下:

  • chaosblade:混沌實驗管理工具,包含建立實驗、銷燬實驗、查詢實驗、實驗環境準備、實驗環境撤銷等命令,是混沌實驗的執行工具,執行方式包含 CLI 和 HTTP 兩種。提供完善的命令、實驗場景、場景引數說明,操作簡潔清晰。
  • chaosblade-spec-go: 混沌實驗模型 Golang 語言定義,便於使用 Golang 語言實現的場景都基於此規範便捷實現。
  • chaosblade-exec-os: 基礎資源實驗場景實現。
  • chaosblade-exec-docker: Docker 容器實驗場景實現,透過呼叫 Docker API 標準化實現。
  • chaosblade-exec-cri: 容器實驗場景實現,透過呼叫 CRI 標準化實現。
  • chaosblade-operator: Kubernetes 平臺實驗場景實現,將混沌實驗透過 Kubernetes 標準的 CRD 方式定義,很方便的使用 Kubernetes 資源操作的方式來建立、更新、刪除實驗場景,包括使用 kubectl、client-go 等方式執行,而且還可以使用上述的 chaosblade cli 工具執行。
  • chaosblade-exec-jvm: Java 應用實驗場景實現,使用 Java Agent 技術動態掛載,無需任何接入,零成本使用,而且支援解除安裝,完全回收 Agent 建立的各種資源。
  • chaosblade-exec-cplus: C++ 應用實驗場景實現,使用 GDB 技術實現方法、程式碼行級別的實驗場景注入。

2. 使用文件

你可以從 Releases 地址下載最新的 chaosblade 工具包,解壓即用。如果想注入 Kubernetes 相關故障場景,需要安裝 chaosblade-operator,詳細的中文使用文件請檢視 chaosblade-help-zh-cn

chaosblade 支援 CLI 和 HTTP 兩種呼叫方式,支援的命令如下:

  • prepare:簡寫 p,混沌實驗前的準備,比如演練 Java 應用,則需要掛載 java agent。例如要演練的應用名是 business,則在目標主機上執行 blade p jvm --process business。如果掛載成功,返回掛載的 uid,用於狀態查詢或者撤銷掛載。
  • revoke:簡寫 r,撤銷之前混沌實驗準備,比如解除安裝 java agent。命令是 blade revoke UID
  • create: 簡寫是 c,建立一個混沌演練實驗,指執行故障注入。命令是 blade create [TARGET] [ACTION] [FLAGS],比如實施一次 Dubbo consumer 呼叫 xxx.xxx.Service 介面延遲 3s,則執行的命令為 blade create dubbo delay --consumer --time 3000 --service xxx.xxx.Service,如果注入成功,則返回實驗的 uid,用於狀態查詢和銷燬此實驗使用。
  • destroy:簡寫是 d,銷燬之前的混沌實驗,比如銷燬上面提到的 Dubbo 延遲實驗,命令是 blade destroy UID
  • status:簡寫 s,查詢準備階段或者實驗的狀態,命令是 blade status UID 或者 blade status --type create
  • server:啟動 web server,暴露 HTTP 服務,可以透過 HTTP 請求來呼叫 chaosblade。例如在目標機器xxxx上執行:blade server start -p 9526,執行 CPU 滿載實驗:curl "http:/xxxx:9526/chaosblade?cmd=create%20cpu%20fullload"

以上命令幫助均可使用 blade help [COMMAND] 或者 blade [COMMAND] -h 檢視,也可檢視新手指南,或者上述中文使用文件,快速上手使用。

3. 安裝

可以選擇編譯安裝或者使用容器映象

3.1 主機安裝

訪問chaosblade下載最新版本的安裝包並解壓到系統path路徑,目前僅支援X86架構。

3.2 容器安裝執行

docker pull chaosbladeio/chaosblade-demodocker pull chaosbladeio/chaosblade-demo
docker run -it --privileged chaosbladeio/chaosblade-demo
# 進入映象之後,可閱讀 README.txt 檔案實施混沌實驗
bash-4.4# ls
README.txt  bin         blade       lib

3.3 k8s安裝

helm repo add chaosblade-io https://chaosblade-io.github.io/charts
helm install chaosblade chaosblade-io/chaosblade-operator --namespace chaosblade
# 預設的映象倉庫是`ghcr.io/chaosblade-io/chaosblade-tool` and `ghcr.io/chaosblade-io/chaosblade-operator`, 增加引數`--set blade.repository` 或者 `--set operator.repository` 修改映象倉庫,例如下:
helm install chaosblade-operator chaosblade-io/chaosblade-operator --namespace chaosblade --set blade.repository=chaosbladeio/chaosblade-tool,operator.repository=chaosbladeio/chaosblade-operator 

# 解除安裝
helm uninstall chaosblade-operator --namespace chaosblade

3.4 編譯安裝

此專案採用 golang 語言編寫,所以需要先安裝最新的 golang 版本,最低支援的版本是 1.11。Clone 工程後進入專案目錄執行以下命令進行編譯:

# 下載專案
https://github.com/chaosblade-io/chaosblade.git
# 編譯安裝,預設會安裝全部測試場景
cd chaosblade
make build

如果在 mac 系統上,編譯當前系統的版本,請執行:

make build_darwin

如果想在 mac 系統上,編譯 linux 系統版本,請執行:

make build_linux

也可以選擇性編譯,比如只需要編譯 cli、os 場景,則執行:

make build_with cli os
# 如果是 mac 系統,執行
make build_with cli os_darwin
# 如果是 mac 系統,想選擇性的編譯 linux 版本的 cli,os,則執行:
ARGS="cli os" make build_with_linux

Arch Linux 安裝 chaosblade-bin

yay -S chaosblade-bin

4. 實踐測試

4.1 幫助文件

 ./blade --help
An easy to use and powerful chaos engineering experiment toolkit

Usage:
  blade [command]

Available Commands:
  check       Check the environment for chaosblade
  create      Create a chaos engineering experiment
  destroy     Destroy a chaos experiment
  help        Help about any command
  prepare     Prepare to experiment
  query       Query the parameter values required for chaos experiments
  revoke      Undo chaos engineering experiment preparation
  status      Query preparation stage or experiment status
  version     Print version info

Flags:
  -d, --debug   Set client to DEBUG mode
  -h, --help    help for blade

支援構造的試驗場景,從下面的命令輸出可以看到支援C++、CPU、磁碟、容器、dubbo、http、jvm、k8s、mysql、網路、程序、mq、指令碼、java servlet等場景或元件的測試試驗。

# ./blade create --help
Create a chaos engineering experiment

Usage:
  blade create [command]

Aliases:
  create, c

Examples:
blade create cpu load --cpu-percent 60

Available Commands:
  aliyun      Aliyun experiment
  aws         Aws experiment
  ck          Clickhouse experiment
  cpu         Cpu experiment
  cri         CRI experiment
  disk        Disk experiment
  druid       Experiment with the Druid
  dubbo       Experiment with the Dubbo
  es          ElasticSearch experiment!
  feign       feign experiment
  file        File experiment
  gateway     gateway experiment!
  hbase       hbase experiment!
  http        http experiment
  jedis       jedis experiment
  jvm         Experiment with the JVM
  k8s         Kubernetes experiment
  kafka       kafka experiment
  lettuce     redis client lettuce experiment
  log         log experiment
  mem         Mem experiment
  mongodb     MongoDB experiment
  mysql       mysql experiment
  network     Network experiment
  nginx       Nginx experiment
  process     Process experiment
  psql        Postgrelsql experiment
  rabbitmq    rabbitmq experiment
  redis       Redis experiment
  redisson    redisson experiment
  rocketmq    Rocketmq experiment,can make message send or pull delay and exception
  script      Script chaos experiment
  security    SpringSecurity login experiment
  servlet     java servlet experiment
  strace      strace experiment
  systemd     Systemd experiment
  tars        tars experiment
  time        Time experiment
  zk          zk experiment

Flags:
  -a, --async             whether to create asynchronously, default is false
  -e, --endpoint string   the create result reporting address. It takes effect only when the async value is true and the value is not empty
  -h, --help              help for create
  -n, --nohup             used to internal async create, no need to config
      --uid string        Set Uid for the experiment, adapt to docker and cri

Global Flags:
  -d, --debug   Set client to DEBUG mode

Use "blade create [command] --help" for more information about a command.

備註

二進位制主機版本的功能較容器形態的功能較豐富,建議使用二進位制版本。

4.2 測試案例

部分測試案例總結如下。

jvm異常測試

# 執行容器
docker run -it --privileged chaosbladeio/chaosblade-demo
# 容器中執行了一個dubbo示例程式,執行如下命令可以看到程式的功能
bash-4.4# curl http://localhost:8080/dubbo/hello?name=dubbo
Hello dubbo, response from provider: 172.17.0.2:20880
bash-4.4# netstat -tulnp
Active Internet connections (only servers)
Proto Recv-Q Send-Q Local Address           Foreign Address         State       PID/Program name
tcp        0      0 :::20880                :::*                    LISTEN      16/java
tcp        0      0 :::8080                 :::*                    LISTEN      16/java
tcp        0      0 ::ffff:127.0.0.1:8005   :::*                    LISTEN      16/java
tcp        0      0 :::8009                 :::*                    LISTEN      16/java

# 進行混沌測試,準備一個java程式試驗環境
bash-4.4# blade prepare jvm --process business
{"code":200,"success":true,"result":"400019538151a8cf"}
bash-4.4#  blade status --type prepare
{
        "code": 200,
        "success": true,
        "result": [
                {
                        "Uid": "400019538151a8cf",
                        "ProgramType": "jvm",
                        "Process": "business",
                        "Port": "44587",
                        "Status": "Running",
                        "Error": "",
                        "CreateTime": "2024-05-31T12:45:46.620634205Z",
                        "UpdateTime": "2024-05-31T12:45:56.864110741Z"
                }
        ]
}

# 構造一個延遲場景。當呼叫com.example.service.DemoService的sayHello方法時,延遲3s。
bash-4.4# blade create dubbo delay --time 3000 --service com.example.service.DemoService --methodname sayHello --consumer
{"code":200,"success":true,"result":"e3861cc4b4bca049"}
# 再次執行curl呼叫介面,檢視效果
bash-4.4# curl http://localhost:8080/dubbo/hello?name=dubbo
chaosblade-mock-TimeoutException,timeout=1000
# 刪除構造的延遲3秒的故障
bash-4.4# blade destroy e3861cc4b4bca049
{"code":200,"success":true,"result":"command: dubbo delay --consumer true --help false --service com.example.service.DemoService --provider false --debug false --methodname sayHello --time 3000"}
bash-4.4# curl http://localhost:8080/dubbo/hello?name=dubbo
Hello dubbo, response from provider: 172.17.0.2:20880
# 使用status命令查詢試驗的狀態
bash-4.4# blade status --type create
{
        "code": 200,
        "success": true,
        "result": [
                {
                        "Uid": "e3861cc4b4bca049",
                        "Command": "dubbo",
                        "SubCommand": "delay",
                        "Flag": "--consumer true --help false --service com.example.service.DemoService --provider false --debug false --methodname sayHello --time 3000",
                        "Status": "Destroyed",
                        "Error": "",
                        "CreateTime": "2024-05-31T12:28:48.91064256Z",
                        "UpdateTime": "2024-05-31T12:31:01.99721936Z"
                }
        ]
}

# 或者使用blade s <UID>檢視

# 構造一個當呼叫服務時,異常丟擲的場景
bash-4.4# blade create jvm throwCustomException --exception java.lang.Exception \
>     --classname com.example.controller.DubboController --methodname hello
{"code":200,"success":true,"result":"44fead600e3c2579"}
bash-4.4# blade status 44fead600e3c2579
{
        "code": 200,
        "success": true,
        "result": {
                "Uid": "44fead600e3c2579",
                "Command": "jvm",
                "SubCommand": "throwCustomException",
                "Flag": "--exception java.lang.Exception --help false --methodname hello --classname com.example.controller.DubboController --debug false",
                "Status": "Success",
                "Error": "",
                "CreateTime": "2024-05-31T12:35:22.602827497Z",
                "UpdateTime": "2024-05-31T12:35:23.010550446Z"
        }
}
bash-4.4# curl http://localhost:8080/dubbo/hello?name=dubbo
...
Request processing failed; nested exception is java.lang.Exception: chaosblade-mock-exception
...
# 刪除構造的異常後,呼叫恢復正常。

cpu加壓測試

使用指導:

# ./blade create cpu load --help
Create chaos engineering experiments with CPU load

Usage:
  blade create cpu fullload

Aliases:
  fullload, fl, load

Examples:

# Create a CPU full load experiment
blade create cpu load

#Specifies two random core's full load
blade create cpu load --cpu-percent 60 --cpu-count 2

# Specifies that the core is full load with index 0, 3, and that the core's index starts at 0
blade create cpu load --cpu-list 0,3

# Specify the core full load of indexes 1-3
blade create cpu load --cpu-list 1-3

# Specified percentage load
blade create cpu load --cpu-percent 60

Flags:
      --blade-release string     Blade release package,use this flag when the channel is ssh
      --cgroup-root string       cgroup root path, default value /sys/fs/cgroup
      --channel string           Select the channel for execution, and you can now select SSH
      --climb-time string        durations(s) to climb
      --cpu-count string         Cpu count
      --cpu-index string         cpu index, user unavailable!
      --cpu-list string          CPUs in which to allow burning (0-3 or 1,3)
      --cpu-percent string       percent of burn CPU (0-100)
  -h, --help                     help for fullload
      --install-path string      install path default /opt/chaosblade,use this flag when the channel is ssh
      --override-blade-release   Override blade release,use this flag when the channel is ssh
      --ssh-host string          Use this flag when the channel is ssh
      --ssh-key string           Use this flag when the channel is ssh
      --ssh-key-passphrase       Use this flag when the channel is ssh
      --ssh-port string          Use this flag when the channel is ssh
      --ssh-user string          Use this flag when the channel is ssh
      --timeout string           set timeout for experiment

Global Flags:
  -a, --async             whether to create asynchronously, default is false
  -d, --debug             Set client to DEBUG mode
  -e, --endpoint string   the create result reporting address. It takes effect only when the async value is true and the value is not empty
  -n, --nohup             used to internal async create, no need to config
      --uid string        Set Uid for the experiment, adapt to docker and cri

cpu加壓測試,使cpu滿負荷執行60秒:

./blade create cpu load --cpu-percent 100 --timeout 60

記憶體加壓測試

使用指導:

./blade create mem load --help
Create chaos engineering experiments with memory load

Usage:
  blade create mem load

Examples:

# The execution memory footprint is 50%
blade create mem load --mode ram --mem-percent 50

# The execution memory footprint is 50%, cache model
blade create mem load --mode cache --mem-percent 50

# The execution memory footprint is 50%, usage contains buffer/cache
blade create mem load --mode ram --mem-percent 50 --include-buffer-cache

# The execution memory footprint is 50%, avoid mem-burn process being killed
blade create mem load --mode ram --mem-percent 50 --avoid-being-killed

# The execution memory footprint is 50% for 200 seconds
blade create mem load --mode ram --mem-percent 50 --timeout 200

# 200M memory is reserved
blade create mem load --mode ram --reserve 200 --rate 100

構造記憶體100%測試,持續60s,執行如下命令後,使用free -m檢視系統記憶體:

blade create mem load --mode ram --mem-percent 100 --timeout 60

磁碟加壓測試

支援磁碟負載加壓,及空間填充測試。可以使用下面命令檢視具體引數:

# IO負載加壓
./blade create disk burn  --help
Increase disk read and write io load

Usage:
  blade create disk burn

Examples:

# The data of rkB/s, wkB/s and % Util were mainly observed. Perform disk read IO high-load scenarios
blade create disk burn --read --path /home

# Perform disk write IO high-load scenarios
blade create disk burn --write --path /home

# Read and write IO load scenarios are performed at the same time. Path is not specified. The default is /
blade create disk burn --read --write
...

# 空間填充測試
./blade create disk  fill --help
Fill the specified directory path. If the path is not directory or does not exist, an error message will be returned.

Usage:
  blade create disk fill

Examples:

# Perform a disk fill of 40G to achieve a full disk (34G available)
blade create disk fill --path /home --size 40000

# Performs populating the disk by percentage, and retains the file handle that populates the disk
Command: "blade c disk fill --path /home --percent 80 --retain-handle

# Perform a fixed-size experimental scenario
blade c disk fill --path /home --reserve 1024
...

5. 面向雲原生

chaosblade-operator 專案是針對雲原生平臺所實現的混沌實驗注入工具,遵循混沌實驗模型規範化實驗場景,把實驗定義為 Kubernetes CRD 資源,將實驗模型對映為 Kubernetes 資源屬性,很友好地將混沌實驗模型與 Kubernetes 宣告式設計結合在一起,在依靠混沌實驗模型便捷開發場景的同時,又可以很好的結合 Kubernetes 設計理念,透過 kubectl 或者編寫程式碼直接呼叫 Kubernetes API 來建立、更新、刪除混沌實驗,而且資源狀態可以非常清晰地表示實驗的執行狀態,標準化實現 Kubernetes 故障注入。除了使用上述方式執行實驗外,還可以使用 chaosblade cli 方式非常方便的執行 kubernetes 實驗場景,查詢實驗狀態等。具體請閱讀:雲原生下的混沌工程實踐

6. 場景大圖

experiments landscape

7. 專案生態

ecosystem

更詳細的功能及最新資訊請訪問官方倉庫檢視。

相關文章