如何测试Kubernetes Operator中Reader接口List/Get方法抛错场景
复现Kubernetes Reader接口Get/List方法错误的实现思路
你可以从单元测试和minikube集成测试两个方向实现,以下是可落地的具体方案:
一、单元测试方案(无需依赖minikube,完全可控)
- 用controller-runtime官方提供的fake client注入错误
初始化fake client时通过WithReaction拦截指定资源的Get/List请求,直接返回自定义错误,示例代码如下:import ( "sigs.k8s.io/controller-runtime/pkg/client/fake" "k8s.io/apimachinery/pkg/runtime" ) // 初始化scheme sch := runtime.NewScheme() _ = clientgoscheme.AddToScheme(sch) // 构造fake client,拦截Pod的List请求返回权限错误 fakeClient := fake.NewClientBuilder().WithScheme(sch).WithReaction( &client.ObjectReaction{ GroupVersionKind: corev1.SchemeGroupVersion.WithKind("Pod"), Reaction: func(action client.Action) (handled bool, ret runtime.Object, err error) { if action.GetVerb() == "list" { return true, nil, errors.New("forbidden: user cannot list pods") } return false, nil, nil }, }, ).Build() - 用gomock mock Reader接口
直接mock整个Reader接口的Get/List方法,调用时指定返回任意错误类型,比如超时、资源不存在、权限拒绝等,不需要和真实集群交互即可覆盖所有错误分支。
二、minikube真实集群复现方案
你之前复现失败大概率是使用了默认高权限ServiceAccount,调整配置即可触发错误:
- 权限拒绝场景:修改Operator绑定的Role/ClusterRole,去掉对应资源的
get/list权限。比如要测Deployment的List错误,就把Role规则里的resources: ["deployments"]对应的verbs: ["get", "list"]删掉,重新apply权限配置后,Operator发起请求就会返回403 Forbidden错误。 - 资源不存在场景:测试Get方法时,直接传入集群中不存在的ObjectKey(比如自定义一个不存在的资源名称、不存在的命名空间),即可触发404 NotFound错误。
- 超时/连接失败场景:调用Get/List时传入已超时的context,示例如下:
也可以在调用时暂停minikube虚拟机,主动触发apiserver连接失败的错误。ctx, cancel := context.WithTimeout(context.Background(), 1*time.Nanosecond) defer cancel() // 此时调用sdk.List会直接返回context deadline exceeded错误 - 非法资源类型场景:传入未注册到scheme的资源对象调用Get/List方法,会直接返回类型不匹配的错误。
- 限流错误场景:给minikube apiserver添加限流参数,短时间内发起大量请求即可触发429 Too Many Requests错误。
注意事项
如果要触发命名空间级别资源的权限错误,修改的是命名空间下的Role;如果是集群级别资源(比如Node、Namespace本身),需要修改ClusterRole的权限,同时要确认Operator运行时绑定的ServiceAccount和你修改权限的ServiceAccount一致。
内容的提问来源于stack exchange,提问作者CSUNNY
相关产品推荐
相关产品推荐

