kubemark模拟k8s计算节点,测试k8s组件性能
需求
物理计算节点有限,难以测试网络组件的性能满不满足5000节点集群需求,在开发测试阶段知道网络插件的性能至关重要。因此使用kubemark来模拟计算节点,都知道使用kubemark需要一个真实的k8s集群和一个kubemark集群。真实的k8s集群已搭建完毕,下面需要搭建kubemark虚拟集群。并在虚拟集群中替换自己客制化的组件。
安装kubemark集群
参考k8s官方文档(链接1):
https://github.com/kubernetes/community/blob/452f681d92d98d6d62dfb24fbc9c8da10935632c/contributors/devel/sig-scalability/kubemark-setup-guide.md
如果以上链接打不开可以先到https://github.com/kubernetes/community/页面,在搜索栏里输入kubemark进行搜索,应该能找到。
构建kubemark镜像
你可以下载已经编译好的镜像,也可以自己编译代码
docker pull staging-k8s.gcr.io/kubemark:latest
如果你下载不了,那么感谢伟大的网友ss104301,可以在https://hub.docker.com/网站找到kubemark镜像,用命令docker pull ss104301/kubemark 下载镜像即可。但是如果你需要定制化kubemark那么就需要自己编译kubemark镜像。编译自己的kubemark镜像不像想象中那么复杂,按照链接1给出的三个步骤即可顺利的编译,这三个步骤在此重复一下:
- i. 下载kurbernetes源码
下载和external-cluster一致的kubernetes release版本,我下载的是kubernetes-release-1.14.zip这个文件。里面已经包含了vendor目录,无需自己再下载第三方库 - ii. 编译kubemark二进制文件
设置好GOPATH环境变量,然后执行命令./hack/build-go.sh cmd/kubemark/ cp $GOPATH/src/k8s.io/kubernetes/_output/bin/kubemark $GOPATH/src/k8s.io/kubernetes/cluster/images/kubemark/
- iii. 构建kubemark镜像
这里Dockerfile中写明该镜像From debian:jessie, 我从debian官网中看到debian:jessie就是debian8,然后到https://hub.docker.com/中找到匹配的版本镜像下载到本地并用命令docker tag打上标签debian:jessie, 然后运行上面的命令就能编译出staging-k8s.gcr.io/kubemark:latest本地镜像。注意,编译的环境要求能连外网。cd $GOPATH/src/k8s.io/kubernetes/cluster/images/kubemark/ make build
- iv. 推送kubemark镜像
docker tag staging-k8s.gcr.io/kubemark:latest {{kubemark_image_registry}}/kubemark:{{kubemark_image_tag}} docker push {{kubemark_image_registry}}/kubemark:{{kubemark_image_tag}}
创建hollow节点
- 创建namespace, configmap 和 secret
文章开头提到kubemark方案需要一个真实的k8s集群,这里kubemark使用该集群的config.注意--from-file后面最好放决对路径,否则会在命令执行的当前找配置文件。或者到文件所在的目录下执行命令。
kubectl create ns kubemark
kubectl create configmap node-configmap -n kubemark --from-literal=content.type="test-cluster"
kubectl create secret generic kubeconfig --type=Opaque --namespace=kubemark --from-file=kubelet.kubeconfig=path/to/kubeletcfg --from-file=kubeproxy.kubeconfig=path/to/kubeproxycfg
我的环境用的配置文件路径分别是/etc/kubernetes/kubelet.kubeconfig和/etc/kubernetes/kube-proxy.kubeconfig,这里要仔细核对,不要填错了。
- 用yaml文件创建hollow节点
可以参考官方模板(链接2)
https://github.com/kubernetes/community/blob/452f681d92d98d6d62dfb24fbc9c8da10935632c/contributors/devel/sig-scalability/hollow-node_simplified_template.yaml
注意: - 参数 {{numreplicas}} 表示的是kubemark集群中hollow节点的数量
- 参数 {{numreplicas}}, {{kubemark_image_registry}} 和{{kubemark_image_tag}} 需要根据你的实际情况填写,其他不需要填写
- 你的真实集群要有足够的资源来运行 {{numreplicas}} 数量的 hollow-node pods
最后,用命令创建hollow-node pods就可以了
kubectl create -f hollow-node_simplified_template.yaml
hollow节点排错
查看hollow-node pods,看出并不正常
describe其中一个pod,发现报错"NetworkPlugin cni failed to set up pod "hollow-node-pvp57_kubemark" network: Voyage:Error making request to create endpoint". 这是因为,我们的真实节点使用的是自定义的网络插件voyage,而下载的镜像是没有这个组件的。怎么办呢?一步一步来。
清除网络插件配置,使hollow-node pods能运行起来
因为目前external-cluster使用的是CNI网络模式,而kubemark集群中并没有该网络插件,因此,我先把网络调试调整成hostonly模式,修改/etc/kurbenetes/kubelet文件中的KUBELET_ARGS配置,使--network-plugin值为空重启kubelet,重新创建kubemark集群。但集群还是起不来,查看各个相关pod的log
[root@k8s-master kubernetes]# kubectl log -n kubemark hollow-node-48wb8 hollow-proxy
可以看出,找不到kubelet配置文件中的ssl认证文件,这时需要修改hollow-node_simplified_template.yaml添加volume共享配置
volumes:
- name: sslconfig-volume
hostPath:
path: /etc/kubernetes/ssl/
...
volumeMounts:
- name: sslconfig-volume
mountPath: /etc/kubernetes/ssl/
然后重新创建,hollow-node pod终于Running起来了,但是查看节点信息,并没有多出来节点。再次查看hollow-node pod的log, 报错如下:
I0331 08:37:56.990844 7 kubelet_node_status.go:72] Attempting to register node hollow-node-c229t
E0331 08:37:56.991809 7 kubelet_node_status.go:94] Unable to register node "hollow-node-c229t" with API server: nodes "hollow-node-c229t" is forbidden: node "k8s-master" is not allowed to modify node "hollow-node-c229t"
E0331 08:37:56.997823 7 kubelet.go:2246] node "hollow-node-c229t" not found
E0331 08:37:57.298099 7 kubelet.go:2246] node "hollow-node-c229t" not found
经查看,是证书的问题,因为我们的external-cluster开启了验证,因此要给每个follow-node指定一个证书。RC改变为使用statefulset,因为这样pod的名称是有一定的规律的,方便证书的生产。后面会附上修改的hollow-node.yaml文件。
编译e2e
还是到编译kubemark的目录,设置好GOPATH环境变量。然后输入命令 make WHAT="test/e2e/e2e.test" ,就在_output/bin目录中生成了e2e.test二进制文件。
测试性能
这里需要先安装ginkgo和gomega,生成kubeconfig文件:kubectl config view -o yaml >> /root/.kube/config . 然后引用上面编译好的e2e二进制文件
_output/bin/e2e.test --kube-master=10.27.244.161 --host=http://10.27.244.161:8080 --ginkgo.focus=":Performance]" --provider=local --kubeconfig=/etc/kubernetes/kubelet.kubeconfig --num-nodes=2 --v=3 > performance.log
然后查看 "pods creation" 关键字来看创建花费的时间。
修改kubemark网络插件
kubemark使用的网络组件是默认的fake cri networking,叫做kubernetes.io/no-op.因此一般情况下不需要部署网络插件,虚拟节点上的容器也会得到一个IP. 但是如果你需要测试自己的网络插件的性能,那么就需要修改kubemark源代码,在hollow_kubelet.go文件中的GetHollowKubeletConfig函数中添加f.ContainerRuntimeOptions.NetworkPluginName = "cni"
即可。注意编译的时候需要先把_output文件夹删除,否则不生效。但是注意,当使用自己的网络插件时,可能需要修改kubelet/dockershim/docker_sandbox.go中的getIPFromPlugin函数。根据插件的不同获取插件指定的IP,否则kubectl查看到的Pod的IP是hollow-node的IP。
网络插件的进程也需要有hollow-node pod在启动时带起来,让网络插件守护进程跑在虚拟节点pod里,监听kubelet的调用。其实虚拟节点上的kubelet进程也是被hollow-node pod启动时带起来的。
修改虚拟节点的资源配置
kubemark创建的hollow-node使用的是cadvisor_fake.go中的默认资源值例如FakeNumCores(CPU核数),FakeMemoryCapacity(内存大小)等等。如果需要修改就修改这里或者引用这些数值的地方,然后重新编译。
屏蔽PreStop处理代码
因为kubemark创建的pod是不真实调用docker-cri接口的,也就是说并没有真实的pod被创建出来。当pod销毁时有PreStop事件需要处理的话,那么会crash,所以需要屏蔽kubelet/kuberuntime/kuberuntime_container.go中的函数executePreStopHook处理PreStop的代码。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· SQL Server 2025 AI相关能力初探
· Linux系列:如何用 C#调用 C方法造成内存泄露
· AI与.NET技术实操系列(二):开始使用ML.NET
· 记一次.NET内存居高不下排查解决与启示
· 探究高空视频全景AR技术的实现原理
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· SQL Server 2025 AI相关能力初探
· AI编程工具终极对决:字节Trae VS Cursor,谁才是开发者新宠?
· 开源Multi-agent AI智能体框架aevatar.ai,欢迎大家贡献代码
· Manus重磅发布:全球首款通用AI代理技术深度解析与实战指南