CCE节点事件中一直出现“镜像回收失败”告警如何解决?
问题现象
节点事件中,重复出现“镜像回收失败”告警,告警示例如下:
wanted to free xx bytes, but freed xx bytes space with errors in image deletion: rpc error: code = Unknown desc = Error response from daemon: conflict: unable to remove repository reference "imageName:tag" (must force) - container 966fce58d9b8 is using its referenced image 50a7aa6fa56a
例如上述告警中提到的容器ID(966fce58d9b8)已经停止运行了,但没有完全被删除。
问题根因
kubelet根据imageGCHighThresholdPercent和imageGCLowThresholdPercent两个配置参数定期回收未在使用中的镜像。如果在节点上使用docker或crictl命令行启动容器,那么在容器停止后,它将处于退出状态,但并未完全删除,这意味着该容器仍然引用着容器镜像。由于kubelet无法感知到非Pod产生的容器,也就无法感知到该容器镜像被引用,因此当kubelet尝试删除容器镜像时,容器运行时会因为容器镜像仍处于被引用的状态而拦截kubelet的删除行为,导致kubelet在定期回收镜像过程中出现失败。
解决方法
登录节点上执行以下命令,过滤出告警提示的容器,确认是否处于exited状态。其中{containerId}需要替换为告警中提到的容器ID。
- 节点使用docker运行时:
docker ps -a | grep {containerId}
- 节点使用containerd运行时:
crictl ps -a | grep {containerId}
如果您确认容器已不再使用,请执行以下命令,彻底清除处于exited状态的容器。其中{containerId}需要替换为告警中提到的容器ID。
- 节点使用docker运行时:
docker rm {containerId}
- 节点使用containerd运行时:
crictl rm {containerId}
删除问题容器后,kubelet下次回收镜像可以正常进行。