今天部署 K8s 集群装 Docker 的经历太魔幻了 —— 用 Ansible 跑安装脚本卡到怀疑人生,我啥配置都没改,隔了一会儿重新跑居然直接好了!先把我的原版代码和整个排查 +“自愈” 过程分享出来。

一、先上我的原版 Ansible 代码(没改一行)

- name: Install Docker Engine on all nodes
  hosts: all  # 这个play将会在inventory中的所有主机上运行
  become: true # 使用sudo权限执行任务
  tasks:
    - name: Ensure required packages for adding repo are installed
      # 使用dnf模块确保dnf-utils存在
      ansible.builtin.dnf:
        name: dnf-utils
        state: present

    - name: Add Docker CE repository
      # 使用get_url模块下载repo文件,这是幂等的
      ansible.builtin.get_url:
        url: https://download.docker.com/linux/centos/docker-ce.repo
        dest: /etc/yum.repos.d/docker-ce.repo
        mode: '0644'

    - name: Install Docker packages
      # 使用dnf模块安装docker-ce, docker-ce-cli, 和 containerd.io
      # 我们也把containerd.io加进来,确保所有CRI工具都通过包管理器安装
      # 加上containerd-ctr是为了确保ctr命令一定存在
      ansible.builtin.dnf:
        name:
          - docker-ce
          - docker-ce-cli
          - containerd.io
        state: present
        update_cache: yes # 安装前先更新dnf缓存

    - name: Start and enable Docker service
      # 使用systemd模块来管理服务
      ansible.builtin.systemd:
        name: docker
        state: started
        enabled: yes

二、卡死的场景:真就卡到一动不动

我第一次跑ansible-playbook install-docker.yml的时候,前面两步(装 dnf-utils、下载 docker-ce.repo)都秒过,到Install Docker packages这一步直接 “定住” 了 —— 终端没任何输出,也不报错,就停在那,等了 10 分钟都没反应,最后只能按 Ctrl+C 中断。

当时我第一反应是:是不是服务器网络断了?或者 yum/dnf 被锁了?

三、我排查了啥(啥配置都没改)

虽然最后没改代码,但我还是先做了基础排查,排除了常见问题:

  1. 查 dnf/yum 进程和锁文件
    ps aux | grep dnf
    ls /var/run/dnf.pid
    
    结果:没有多余进程,也没有锁文件,排除 “进程占用” 问题;
  2. 手动在节点跑安装命令:登录 k8s-node1,执行dnf install -y docker-ce docker-ce-cli containerd.io,发现命令也是卡在 “下载包” 阶段,不过能看到是在连 Docker 官方源(download.docker.com),只是速度慢到几乎不动;
  3. 没改配置,就等了会儿重新跑:我本来准备改阿里云源的,结果接了个电话回来,想着再试一次吧,直接重新执行ansible-playbook install-docker.yml—— 好家伙,这次Install Docker packages步骤虽然慢,但居然一步步跑完了!最后Start and enable Docker service也成功了,查systemctl status docker显示 running,彻底懵圈~

四、为啥 “没改配置就好了”?大概率是这两个原因

虽然代码没动,但结合排查过程,我复盘出大概率是这两个点:

  1. 官方源临时通了:我用的是 Docker 官方源(download.docker.com),国内访问本来就不稳定,第一次跑的时候刚好赶上源节点拥堵 / 网络波动,包下载不下来就卡着;等了一会儿网络恢复,或者源节点不挤了,第二次跑就成功了(本质是 “网络偶发问题”);
  2. 第一次中断后缓存生效了:第一次跑的时候,dnf 虽然卡着,但其实已经开始更新缓存(update_cache: yes),中断后缓存其实已经更完了;第二次跑的时候不用再更缓存,直接下载包,刚好赶上网络好转,就顺利装完了。

五、给和我一样的新手提个醒(避坑关键)

虽然这次 “自愈” 了,但这种靠运气的事儿不能赌,还是要知道怎么从根上避免:

  1. 优先换国内源:我的代码里用的是官方 repo,建议还是换成阿里云的,把Add Docker CE repository步骤改成这样,彻底解决源慢的问题:

    yaml

    - name: Add Docker CE repository (Aliyun mirror)
      ansible.builtin.copy:
        content: |
          [docker-ce-stable]
          name=Docker CE Stable - $basearch
          baseurl=https://mirrors.aliyun.com/docker-ce/linux/centos/$releasever/$basearch/stable
          enabled=1
          gpgcheck=1
          gpgkey=https://mirrors.aliyun.com/docker-ce/linux/centos/gpg
        dest: /etc/yum.repos.d/docker-ce.repo
        mode: '0644'
    
  2. 卡顿时别直接 Ctrl+C:先等 5-10 分钟,或者开另一个终端看节点上的dnf进程(ps aux | grep dnf),如果进程还在跑,说明只是下载慢,不是真卡死;
  3. 加超时和重试:在Install Docker packages步骤里加timeout: 300和重试,避免单次卡壳就失败:

    yaml

    - name: Install Docker packages
      ansible.builtin.dnf:
        name:
          - docker-ce
          - docker-ce-cli
          - containerd.io
        state: present
        update_cache: yes
        timeout: 300 # 5分钟超时
      retries: 2 # 失败后重试2次
      delay: 10 # 每次重试间隔10秒
    

Logo

腾讯云面向开发者汇聚海量精品云计算使用和开发经验,营造开放的云计算技术生态圈。

更多推荐