扩展 Chaos Daemon 接口
本页面由 PageTurner AI 翻译(测试版)。未经项目官方认可。 发现错误? 报告问题 →
在添加新的混沌实验类型中,您已添加了HelloWorldChaos,该实验可在 Chaos Controller Manager 的日志中输出Hello world!。
若要让HelloWorldChaos向目标 Pod 注入故障,您需要扩展 Chaos Daemon 的接口。
建议继续操作前先阅读 Chaos Mesh 架构。
本文涵盖以下内容:
选择器
在api/v1alpha1/helloworldchaos_type.go中,您已定义包含ContainerSelector的HelloWorldSpec:
// HelloWorldChaosSpec defines the desired state of HelloWorldChaos
type HelloWorldChaosSpec struct {
// ContainerSelector specifies the target for injection
ContainerSelector `json:",inline"`
// Duration represents the duration of the chaos
// +optional
Duration *string `json:"duration,omitempty"`
// RemoteCluster represents the remote cluster where the chaos will be deployed
// +optional
RemoteCluster string `json:"remoteCluster,omitempty"`
}
//...
// GetSelectorSpecs is a getter for selectors
func (obj *HelloWorldChaos) GetSelectorSpecs() map[string]interface{} {
return map[string]interface{}{
".": &obj.Spec.ContainerSelector,
}
}
在 Chaos Mesh 中,选择器用于定义混沌实验的作用范围,包括目标命名空间、注解、标签等。
选择器也可以是更具体的值(例如AWSChaos中的AWSSelector)。通常每个混沌实验只需一个选择器,但像NetworkChaos这样的实验例外——当进行网络分区时需要两个选择器来标识两个对象。
关于选择器的更多信息,请参阅定义混沌实验作用域。
实现 gRPC 接口
为使 Chaos Daemon 能接收 Chaos Controller Manager 的请求,您需要实现新的 gRPC 接口。
-
在
pkg/chaosdaemon/pb/chaosdaemon.proto中添加 RPC:service ChaosDaemon {
...
rpc ExecHelloWorldChaos(ExecHelloWorldRequest) returns (google.protobuf.Empty) {}
}
message ExecHelloWorldRequest {
string container_id = 1;
}然后执行以下命令更新相关
chaosdaemon.pb.go文件:make proto -
在 Chaos Daemon 中实现 gRPC 服务。
在
pkg/chaosdaemon目录下创建helloworld_server.go文件,内容如下:package chaosdaemon
import (
"context"
"github.com/golang/protobuf/ptypes/empty"
"github.com/chaos-mesh/chaos-mesh/pkg/bpm"
"github.com/chaos-mesh/chaos-mesh/pkg/chaosdaemon/pb"
)
func (s *DaemonServer) ExecHelloWorldChaos(ctx context.Context, req *pb.ExecHelloWorldRequest) (*empty.Empty, error) {
log := s.getLoggerFromContext(ctx)
log.Info("ExecHelloWorldChaos", "request", req)
pid, err := s.crClient.GetPidFromContainerID(ctx, req.ContainerId)
if err != nil {
return nil, err
}
cmd := bpm.DefaultProcessBuilder("sh", "-c", "ps aux").
SetContext(ctx).
SetNS(pid, bpm.MountNS).
Build(ctx)
out, err := cmd.Output()
if err != nil {
return nil, err
}
if len(out) != 0 {
log.Info("cmd output", "output", string(out))
}
return &empty.Empty{}, nil
}当
chaos-daemon接收到ExecHelloWorldChaos请求后,您将看到当前容器内的进程列表。 -
在应用混沌实验时发送 gRPC 请求
每个混沌实验都有生命周期:先
apply再recover。但某些混沌实验默认无法恢复(例如 PodChaos 中的 PodKill 和 HelloWorldChaos),这类实验称为 OneShot 实验。我们在HelloWorldChaos模式中定义的+chaos-mesh:oneshot=true就是标记。当
HelloWorldChaos处于apply阶段时,混沌控制器管理器需要向 chaos-daemon 发送请求。需更新controllers/chaosimpl/helloworldchaos/types.go:func (impl *Impl) Apply(ctx context.Context, index int, records []*v1alpha1.Record, obj v1alpha1.InnerObject) (v1alpha1.Phase, error) {
impl.Log.Info("Apply helloworld chaos")
decodedContainer, err := impl.decoder.DecodeContainerRecord(ctx, records[index], obj)
if err != nil {
return v1alpha1.NotInjected, err
}
pbClient := decodedContainer.PbClient
containerId := decodedContainer.ContainerId
_, err = pbClient.ExecHelloWorldChaos(ctx, &pb.ExecHelloWorldRequest{
ContainerId: containerId,
})
if err != nil {
return v1alpha1.NotInjected, err
}
return v1alpha1.Injected, nil
}
func (impl *Impl) Recover(ctx context.Context, index int, records []*v1alpha1.Record, obj v1alpha1.InnerObject) (v1alpha1.Phase, error) {
impl.Log.Info("Recover helloworld chaos")
return v1alpha1.NotInjected, nil
}信息由于无需恢复
HelloWorldChaos,因为HelloWorldChaos是 OneShot 实验。您可根据实际需求在开发的其他混沌实验类型中实现恢复逻辑。
验证 HelloWorldChaos 输出
现在可以验证 HelloWorldChaos 的输出效果:
-
按添加新混沌实验类型文档说明构建 Docker 镜像,并加载到集群
备注若使用 minikube,请注意部分版本无法覆盖同标签的现有镜像。建议先删除旧镜像再加载新镜像。
-
Update Chaos Mesh:
-
部署测试用 Pod:
kubectl apply -f https://raw.githubusercontent.com/chaos-mesh/apps/master/ping/busybox-statefulset.yaml -
创建
hello-busybox.yaml文件,内容如下:apiVersion: chaos-mesh.org/v1alpha1
kind: HelloWorldChaos
metadata:
name: hello-busybox
namespace: chaos-mesh
spec:
selector:
namespaces:
- busybox
mode: all
duration: 1h -
运行以下命令:
kubectl apply -f hello-busybox.yaml
# helloworldchaos.chaos-mesh.org/hello-busybox created-
现在检查
chaos-controller-manager日志中是否出现Apply helloworld chaos记录:kubectl logs -n chaos-mesh chaos-controller-manager-xxx示例输出:
2023-07-16T08:20:46.823Z INFO records records/controller.go:149 apply chaos {"id": "busybox/busybox-0/busybox"}
2023-07-16T08:20:46.823Z INFO helloworldchaos helloworldchaos/types.go:27 Apply helloworld chaos -
检查 Chaos Daemon 的日志:
kubectl logs -n chaos-mesh chaos-daemon-xxx示例输出:
2023-07-16T08:20:46.833Z INFO chaos-daemon.daemon-server chaosdaemon/server.go:187 ExecHelloWorldChaos {"namespacedName": "chaos-mesh/hello-busybox", "request": "container_id:\"docker://5e01e76efdec6aa0934afc15bb80e121d58b43c529a6696a01a242f7ac68f201\""}
2023-07-16T08:20:46.834Z INFO chaos-daemon.daemon-server.background-process-manager.process-builder pb/chaosdaemon.pb.go:4568 build command {"namespacedName": "chaos-mesh/hello-busybox", "command": "/usr/local/bin/nsexec -m /proc/104710/ns/mnt -- sh -c ps aux"}
2023-07-16T08:20:46.841Z INFO chaos-daemon.daemon-server chaosdaemon/server.go:187 cmd output {"namespacedName": "chaos-mesh/hello-busybox", "output": "PID USER TIME COMMAND\n 1 root 0:00 sh -c echo Container is Running ; sleep 3600\n"}
2023-07-16T08:20:46.856Z INFO chaos-daemon.daemon-server chaosdaemon/server.go:187 ExecHelloWorldChaos {"namespacedName": "chaos-mesh/hello-busybox", "request": "container_id:\"docker://bab4f632a0358529f7d72d35e014b8c2ce57438102d99d6174dd9df52d093e99\""}
2023-07-16T08:20:46.864Z INFO chaos-daemon.daemon-server.background-process-manager.process-builder pb/chaosdaemon.pb.go:4568 build command {"namespacedName": "chaos-mesh/hello-busybox", "command": "/usr/local/bin/nsexec -m /proc/104841/ns/mnt -- sh -c ps aux"}
2023-07-16T08:20:46.867Z INFO chaos-daemon.daemon-server chaosdaemon/server.go:187 cmd output {"namespacedName": "chaos-mesh/hello-busybox", "output": "PID USER TIME COMMAND\n 1 root 0:00 sh -c echo Container is Running ; sleep 3600\n"}
您将看到两条独立的
ps aux输出记录,分别对应两个不同的 Pod。 -
后续规划
如果您在操作过程中遇到任何问题,请在 Chaos Mesh 仓库提交 issue。
若想深入了解实现原理,可继续阅读 controllers/README.md 和各类控制器的源代码。
现在您已准备好成为 Chaos Mesh 的开发者!欢迎访问 Chaos Mesh issues 寻找入门任务并开始贡献吧!