混沌工程 | 你所不知道的 ChaosBlade 那些事

1

项目背景

阿里巴巴内部从最先引入混沌工程解决微服务的依赖问题,到业务服务、云服务稳态验证,进一步升级到公共云、专有云的业务连续性保障,以及在验证云原生系统的稳定性等方面积累了比较丰富的场景和实践经验。而且当时混沌工程相关的开源工具存在场景能力分散、上手难度大、缺乏实验模型标准,场景难以扩展和沉淀等问题。这些问题就会致使很难实现平台化,你很难经过一个平台去囊括这些工具。因此咱们开源了 ChaosBlade 这个混沌工程实验执行工具,目的是服务于混沌工程社区,共同推动混沌工程领域的发展。node

项目介绍

ChaosBlade 项目托管在 Github 平台,放在 chaosblade-io 组织下,方便项目管理和社区发展。设计 ChaosBlade 初期就考虑了易用性和场景扩展的便捷性,方便你们上手使用以及根据各自须要扩展更多的实验场景,遵循混沌实验模型提供了统一的操做简洁的执行工具,而且根据领域划分将场景实现封装成一个一个单独的项目,方便实现领域内场景扩展。目前包含的场景领域以下:mysql

  • 基础资源:好比 CPU、内存、网络、磁盘、进程等实验场景
  • Java 应用:好比数据库、缓存、消息、JVM 自己、微服务等,还能够指定任意类方法注入各类复杂的实验场景
  • C++ 应用:好比指定任意方法或某行代码注入延迟、变量和返回值篡改等实验场景
  • Docker 容器:好比杀容器、容器内 CPU、内存、网络、磁盘、进程等实验场景
  • Kubernetes 平台:好比节点上 CPU、内存、网络、磁盘、进程实验场景,Pod 网络和 Pod 自己实验场景如杀 Pod,容器的实验场景如上述的 Docker 容器实验场景
  • 云资源:好比阿里云 ECS 宕机等实验场景

以上场景领域都单独封装成一个项目来实现,目前包含的项目以下:git

  • chaosblade:混沌实验管理工具,包含建立实验、销毁实验、查询实验、实验环境准备、实验环境撤销等命令,是混沌实验的执行工具,执行方式包含 CLI 和 HTTP 两种。提供完善的命令、实验场景、场景参数说明,操做简洁清晰。
  • chaosblade-spec-go: 混沌实验模型 Golang 语言定义,便于使用 Golang 语言实现的场景都基于此规范便捷实现。
  • chaosblade-exec-os: 基础资源实验场景实现。
  • chaosblade-exec-docker: Docker 容器实验场景实现,经过调用 Docker API 标准化实现。
  • chaosblade-operator: Kubernetes 平台实验场景实现,将混沌实验经过 Kubernetes 标准的 CRD 方式定义,很方便的使用 Kubernetes 资源操做的方式来建立、更新、删除实验场景,包括使用 kubectl、client-go 等方式执行,并且还可使用上述的 chaosblade cli 工具执行。
  • chaosblade-exec-jvm: Java 应用实验场景实现,使用 Java Agent 技术动态挂载,无需任何接入,零成本使用,并且支持卸载,彻底回收 Agent 建立的各类资源。
  • chaosblade-exec-cplus: C++ 应用实验场景实现,使用 GDB 技术实现方法、代码行级别的实验场景注入。

以上项目都遵循混沌实验模型定义实验场景,这样不只实现实验场景水平领域扩展,并且每一个场景领域单独一个项目,使用该领域下标准方式去设计实现场景,因此很方便的实现领域内场景垂直扩展。github

除了实验场景相关项目,还有相关的文档项目:sql

实验模型

前面提到 ChaosBlade 项目是遵循混沌实验模型设计,不只简化了实验场景定义,并且能够很方便的扩展场景,而且经过 chaosblade cli 工具能够统一调用,便于构建上层的混沌实验平台。下面经过实验模型的推导、介绍、意义和具体的应用来详细介绍此模型。docker

实验模型的推导

目前的混沌实验主要包含故障模拟,咱们通常对故障的描述以下:数据库

  • 10.0.0.1 机器上挂载的 A 磁盘满形成了服务不可用
  • 全部节点上的 B dubbo 服务由于执行缓慢形成上游 A dubbo 服务调用延迟,从而形成用户访问缓慢
  • Kubernetes A 集群中 B 节点上 CPU 全部核使用率满载,形成 A 集群中的 Pod 调度异常
  • Kubernetes C 集群中 D Pod 网络异常,形成 D 相关的 Service 访问异常

经过上述,咱们可使用如下句式来描述故障:由于某某机器(或集群中的资源,如 Node,Pod)上的哪一个组件发生了什么故障,从而形成了相关影响。咱们也能够经过下图来看故障描述拆分:
2_jpegjson

能够经过这四部分来描述现有的故障场景,全部咱们抽象出了一个故障场景模型,也称为混沌实验模型
3_jpegapi

实验模型的介绍

此实验模型详细描述以下:缓存

  • Scope: 实验实施范围,指具体实施实验的机器、集群及其资源等
  • Target: 实验靶点,指实验发生的组件。如基础资源场景中的 CPU、网络、磁盘等,Java 场景中的应用组件如 Dubbo、Redis、RocketMQ、JVM 等,容器场景中的 Node、Pod、Container自身等
  • Matcher: 实验规则匹配器,根据所配置的 Target,定义相关的实验匹配规则,能够配置多个。因为每一个 Target 可能有各自特殊的匹配条件,好比 RPC 领域的 Dubbo、gRPC 能够根据服务提供者提供的服务和服务消费者调用的服务进行匹配,缓存领域的 Redis,能够根据 set、get 操做进行匹配。还能够对 matcher 进行扩展,好比扩展实验场景执行策略,控制实验触发时间。
  • Action: 指实验模拟的具体场景,Target 不一样,实施的场景也不同,好比磁盘,能够演练磁盘满,磁盘 IO 读写高,磁盘硬件故障等。若是是应用,能够抽象出延迟、异常、返回指定值(错误码、大对象等)、参数篡改、重复调用等实验场景。若是是容器服务,能够模拟 Node、Pod、Container 资源异常或者其上的基础资源异常等。

使用此模型能够很清晰表达出如下实施混沌实验须要明确的问题:

  • 混沌实验的实施范围是什么
  • 实施混沌实验的对象是什么
  • 实验对象触发实验的条件有哪些
  • 具体实施什么实验场景

实验模型的意义

此模型具备如下特色:

  • 简洁:层次清晰,通俗易懂
  • 通用:覆盖目前全部的故障场景,包含基础资源、应用服务、容器服务、云资源等
  • 易实现:很方便的定义清晰的接口规范,实验场景扩展实现简单
  • 语言、领域无关:能够扩展多语言、多领域的模型实现

此模型具备如下的意义:

  • 更精准的描述混沌实验场景
  • 更好的理解混沌实验注入
  • 方便沉淀现有的实验场景
  • 依据模型发掘更多的场景
  • 混沌实验工具更加规范、简洁

实验模型的应用

ChaosBlade 下的项目遵循此混沌实验模型设计,须要注意的是此模型定义了混沌实验场景如何设计,可是实验场景的具体实现每一个领域各不相同,因此将 ChaosBlade 依据领域实现封装成各自独立的项目,每一个项目根据各领域的最佳实践来实现,不只能知足各领域使用习惯,并且还能够经过混沌实验模型来创建与 chaosblade cli 项目的关系,方便使用 chaosblade 来统一调用,各领域下的实验场景依据混沌实验模型生成 yaml 文件描述,暴露给上层混沌实验平台,混沌实验平台根据实验场景描述文件的变动,自动感知实验场景的变化,无需新增场景时再作平台开发,使混沌平台更加专一于混沌工程其余部分。如下分为基于混沌实验模型的 chaosblade cli 设计、基于混沌实验模型的 chaosblade operator 设计和基于混沌实验模型构建混沌实验平台三部分详细介绍混沌实验模型的应用。

基于混沌实验模型的 chaosblade cli 设计

4_jpeg

chaosblade 项目自己使用 Golang 构建,解压即用,工具采用 CLI 方式执行,使用简单,具有完善的命令提示。根据 chaosblade-spec-go 项目对混沌实验模型的定义,解析遵循混沌实验模型实现的实验场景 yaml 描述,将实验场景转换为 cobra 框架所支持的命令参数,实现变量参数化、参数规范化,并且将整个实验对象化,每一个实验对象都会有个 UID,方便管理。
5_jpeg

经过一个具体的实验场景来讲明 chaosblade cli 的使用。
6_jpeg

咱们执行的实验是对其中一个 provider 服务实例注入调用 mk-demo 数据库延迟的故障,能够看到上图左下角,这个就是对 demo 数据库注入延迟的命令,能够看出命令很是简洁清晰,好比很明确的表达出咱们的实验目标是 mysql,咱们的实验场景是作延迟,后面这些都是这些数据库的匹配器,好比表,查询类型,还有控制实验的影响条数等等,使用 ChaosBlade 能够颇有效的控制实验的爆炸半径。执行这条命令就能够对这台机器的 provider 服务注入故障,你们能够看到我注入故障以后,这里这个图就是我马上收到了钉钉的报警,那么这个 case 是符合预期的 case,可是即便符合预期的case,也是有价值的,须要相关的开发和运维人员是要去排查延迟的问题根因并恢复,有助于提升故障应急效率。
chaosblade 的中文使用文档:https://chaosblade-io.gitbook.io/chaosblade-help-zh-cn

基于混沌实验模型的 chaosblade operator 设计

7_jpeg

chaosblade-operator 项目是针对 Kubernetes 平台所实现的混沌实验注入工具,遵循上述混沌实验模型规范化实验场景,把实验定义为 Kubernetes CRD 资源,将实验模型中的四部分映射为 Kubernetes 资源属性,很友好的将混沌实验模型与 Kubernetes 声明式设计结合在一块儿,依靠混沌实验模型便捷开发场景的同时,又能够很好的结合 Kubernetes 设计理念,经过 kubectl 或者编写代码直接调用 Kubernetes API 来建立、更新、删除混沌实验,并且资源状态能够很是清晰的表示实验的执行状态,标准化实现 Kubernetes 故障注入。除了使用上述方式执行实验外,还可使用 chaosblade cli 方式很是方便的执行 kubernetes 实验场景,查询实验状态等。
遵循混沌实验模型实现的 chaosblade operator 除上述优点以外,还能够实现基础资源、应用服务、Docker 容器等场景复用,大大方便了 Kubernetes 场景的扩展,因此在符合 Kubernetes 标准化实现场景方式之上,结合混沌实验模型能够更有效、更清晰、更方便的实现、使用混沌实验场景。
下面经过一个具体的案例来讲明 chaosblade-operator 的使用:对 cn-hangzhou.192.168.0.205 节点本地端口 40690 访问模拟 60% 的网络丢包。
使用 yaml 配置方式,使用 kubectl 来执行实验

apiVersion: chaosblade.io/v1alpha1
kind: ChaosBlade
metadata:
  name: loss-node-network-by-names
spec:
  experiments:
  - scope: node
    target: network
    action: loss
    desc: "node network loss"
    matchers:
    - name: names
      value: ["cn-hangzhou.192.168.0.205"]
    - name: percent
      value: ["60"]
    - name: interface
      value: ["eth0"]
    - name: local-port
      value: ["40690"]

执行实验:

kubectl apply -f loss-node-network-by-names.yaml

查询实验状态,返回信息以下(省略了 spec 等内容):

~ » kubectl get blade loss-node-network-by-names -o json                                                            
{
    "apiVersion": "chaosblade.io/v1alpha1",
    "kind": "ChaosBlade",
    "metadata": {
        "creationTimestamp": "2019-11-04T09:56:36Z",
        "finalizers": [
            "finalizer.chaosblade.io"
        ],
        "generation": 1,
        "name": "loss-node-network-by-names",
        "resourceVersion": "9262302",
        "selfLink": "/apis/chaosblade.io/v1alpha1/chaosblades/loss-node-network-by-names",
        "uid": "63a926dd-fee9-11e9-b3be-00163e136d88"
    },
        "status": {
        "expStatuses": [
            {
                "action": "loss",
                "resStatuses": [
                    {
                        "id": "057acaa47ae69363",
                        "kind": "node",
                        "name": "cn-hangzhou.192.168.0.205",
                        "nodeName": "cn-hangzhou.192.168.0.205",
                        "state": "Success",
                        "success": true,
                        "uid": "e179b30d-df77-11e9-b3be-00163e136d88"
                    }
                ],
                "scope": "node",
                "state": "Success",
                "success": true,
                "target": "network"
            }
        ],
        "phase": "Running"
    }
}

经过以上内容能够很清晰的看出混沌实验的运行状态,执行如下命令中止实验:

kubectl delete -f loss-node-network-by-names.yaml

或者直接删除此 blade 资源

kubectl delete blade loss-node-network-by-names

还能够编辑 yaml 文件,更新实验内容执行,chaosblade operator 会完成实验的更新操做。

使用 chaosblade cli 的 blade 命令执行

blade create k8s node-network loss --percent 60 --interface eth0 --local-port 40690 --kubeconfig config --names cn-hangzhou.192.168.0.205

若是执行失败,会返回详细的错误信息;若是执行成功,会返回实验的 UID:

{"code":200,"success":true,"result":"e647064f5f20953c"}

可经过如下命令查询实验状态:

blade query k8s create e647064f5f20953c --kubeconfig config

{
  "code": 200,
  "success": true,
  "result": {
    "uid": "e647064f5f20953c",
    "success": true,
    "error": "",
    "statuses": [
      {
        "id": "fa471a6285ec45f5",
        "uid": "e179b30d-df77-11e9-b3be-00163e136d88",
        "name": "cn-hangzhou.192.168.0.205",
        "state": "Success",
        "kind": "node",
        "success": true,
        "nodeName": "cn-hangzhou.192.168.0.205"
      }
    ]
  }
}

销毁实验:

blade destroy e647064f5f20953c

除了上述两种方式调用外,还可使用 kubernetes client-go 方式执行,具体可参考:https://github.com/chaosblade-io/chaosblade/blob/master/exec/kubernetes/executor.go 代码实现。

经过上述介绍,能够看出在设计 ChaosBlade 项目初期就考虑了云原生实验场景,将混沌实验模型与 Kubernetes 设计理念友好的结合在一块儿,不只能够遵循 Kubernetes 标准化实现,还能够复用其余领域场景和 chaosblade cli 调用方式,所谓的历史包袱根本不存在 :-)。

基于混沌实验模型构建混沌实验平台

前面也提到了遵循混沌实验模型实现的实验场景,可经过 yaml 文件来描述,上层实验平台能够自动感知实验场景的变动,无需平台再作开发,达到实验平台与实验场景解耦的目的,使你们能够更加专一于混沌实验平台自己的开发上。下面拿 AHAS Chaos 平台举例来讲明如何基于混沌实验模型和 ChaosBlade 构建混沌实验平台。
8_jpeg

能够看到:

  • chaosblade 会合并全部领域场景的 yaml 文件,提供给 ChaosBlade SDK
  • ChaosBlade SDK 感知 yaml 文件变化,从新解析场景描述文件,透传给上层平台,包含场景和场景参数的变动
  • ChaosBlade SDK 透传用户在平台上所配置的参数,调用 chaosblade 工具执行
  • chaosblade 工具会根据调用参数,和解析各领域 yaml 场景描述文件来调用不一样的执行器

总结

混沌实验模型的应用可概括为如下几点:

  • 混沌实验模型使实验场景变量参数化,参数规范化
  • 可遵循模型实现实验场景领域化的水平扩展
  • 可将混沌实验模型和领域内标准化实现相结合,便捷实现领域内场景垂直扩展
  • 上层的领域场景能够复用遵循混沌实验模型定义的场景
  • 经过混沌实验模型声明的场景描述能够很好的接入到 chaosblade cli 中
  • 遵循实验模型能够很方便的构建上层混沌实验平台

项目意义

混沌工程领域已提出多年,混沌工程社区的每个人都贡献着本身的力量来完善整个混沌工程领域体系,尤为是混沌工程理论的提出推进了整个混沌工程领域快速发展。咱们在阿里巴巴内部实践混沌工程不少年,深知落地混沌工程之路充满各类挑战,也知道注入混沌实验只是混沌工程中的一环,混沌工程背后的思考、落地方案和实践经验也是很重要的一部分。咱们只是想把咱们认为好用的内部工具奉献给社区,随后将刚才提到的实践经验也经过各类渠道分享给你们,你们能够将此工具与实践经验相结合,做为企业落地混沌工程的一个入手点,共同推动混沌工程领域的进步,仅此而已。
上述详细介绍了 ChaosBlade 工具的设计和背后的思考,以及将混沌实验模型与各领域标准实现相结合的优点,欢迎对高可用架构感兴趣的各位加入到 ChaosBlade 社区中来,加入到混沌工程社区中来。总而言之,ChaosBlade 相信:开源世界中,任何帮助都是贡献。

将来规划

ChaosBlade 社区在加强原有领域的同时,好比加强云原生领域场景,还会增长更多领域的场景,例如:

  • Golang 应用混沌实验场景
  • NodeJS 应用混沌实验场景

除实验场景外,还会如下规划:

  • 提供一个混沌实验平台供你们使用
  • 完善 ChaosBlade 各项目的开发文档
  • 完善 chaosblade 工具的英文文档

欢迎你们加入,一块儿共建,不限于:

  • bug report
  • feature request
  • performance issue
  • help wanted
  • doc incomplete
  • test missing
  • feature design
  • any question on project

ChaosBlade 项目才刚刚开始,欢迎开源爱好者在使用 ChaosBlade 过程当中产生的任何想法和问题,均可以经过 issue 或者 pull request 的方式反馈到 Github 上。

 


查看更多:https://yq.aliyun.com/articles/743102?utm_content=g_1000102888

上云就看云栖号:更多云资讯,上云案例,最佳实践,产品入门,访问:https://yqh.aliyun.com/

相关文章
相关标签/搜索