1. 为什么选择Ubuntu 20.04 LTS作为Docker运行环境

作为长期支持版本,Ubuntu 20.04 LTS(Focal Fossa)在服务器和工作站领域保持着惊人的市场占有率。根据2023年W3Techs的统计数据,全球超过37%的Linux生产环境运行在这个版本上。选择它作为Docker宿主机的优势显而易见:

  • 长达5年的官方支持周期 :Canonical对LTS版本提供至少5年的安全更新,这意味着你的Docker基础环境将获得持续的安全补丁
  • 内核版本完美适配 :默认搭载的5.4 LTS内核包含完整的cgroups v2和overlayfs支持,这些都是Docker运行的核心依赖
  • 企业级稳定性 :相比滚动更新的发行版,Ubuntu LTS经过更严格的测试验证,特别适合需要长期运行的容器环境

我在实际运维中发现,使用非LTS版本部署Docker时,经常遇到内核模块不兼容的问题。例如某个客户在Ubuntu 21.10上部署的Docker集群就曾因为aufs驱动突然被弃用导致大规模容器崩溃。而LTS版本则能避免这类"技术断崖"。

2. 安装前的系统准备

2.1 硬件虚拟化支持检查

虽然Docker可以运行在没有硬件虚拟化的环境,但启用VT-x/AMD-V能显著提升性能。运行以下命令验证:

grep -E --color 'vmx|svm' /proc/cpuinfo

如果输出中包含vmx(Intel)或svm(AMD)标记,说明CPU支持虚拟化。如果没有输出,需要:

  1. 进入BIOS启用VT-x/AMD-V(不同主板设置路径不同,通常位于Advanced或Security选项卡)
  2. 对于云服务器,可能需要联系供应商开启嵌套虚拟化

注意:某些超极本默认禁用VT-x以节省电量,这时需要在电源管理中关闭"Intel Virtualization Technology for Directed I/O (VT-d)"

2.2 系统更新与依赖安装

保持系统最新是避免依赖冲突的关键:

sudo apt update && sudo apt upgrade -y
sudo apt install -y apt-transport-https ca-certificates curl software-properties-common gnupg lsb-release

这里特别说明每个包的作用:

  • apt-transport-https :允许apt通过HTTPS协议访问仓库
  • ca-certificates :确保SSL证书验证正常
  • curl :用于下载Docker的GPG密钥
  • software-properties-common :提供add-apt-repository命令
  • gnupg :处理加密签名验证
  • lsb-release :获取系统版本信息

3. Docker官方仓库配置

3.1 安全密钥添加

Docker官方建议始终通过GPG密钥验证软件包真实性:

curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo gpg --dearmor -o /usr/share/keyrings/docker-archive-keyring.gpg

这个命令做了三件事:

  1. 通过HTTPS下载Docker的GPG公钥
  2. 使用gpg --dearmor转换密钥格式
  3. 将密钥保存到系统可信密钥环

3.2 仓库源设置

根据CPU架构选择正确的仓库源(以下以x86_64为例):

echo "deb [arch=amd64 signed-by=/usr/share/keyrings/docker-archive-keyring.gpg] https://download.docker.com/linux/ubuntu $(lsb_release -cs) stable" | sudo tee /etc/apt/sources.list.d/docker.list > /dev/null

参数解析:

  • arch=amd64 :明确指定CPU架构
  • signed-by :指向我们刚刚添加的密钥
  • $(lsb_release -cs) :自动获取系统代号(如focal)

更新apt缓存:

sudo apt update

4. Docker引擎安装与验证

4.1 安装指定版本

建议安装特定版本而非最新版以确保稳定性:

sudo apt install -y docker-ce=5:20.10.14~3-0~ubuntu-focal docker-ce-cli=5:20.10.14~3-0~ubuntu-focal containerd.io

版本号说明:

  • 5: :Docker的epoch版本
  • 20.10.14 :主版本号
  • ~3-0~ubuntu-focal :针对Ubuntu 20.04的构建版本

锁定版本防止意外升级:

sudo apt-mark hold docker-ce docker-ce-cli containerd.io

4.2 服务启动与验证

启动Docker服务并设置开机自启:

sudo systemctl enable --now docker

验证安装成功的黄金标准是运行测试容器:

sudo docker run --rm hello-world

预期看到以下输出:

Hello from Docker!
This message shows that your installation appears to be working correctly.
...

5. 非root用户权限配置

5.1 docker用户组管理

默认情况下只有root用户能运行Docker命令,这既不安全也不方便。正确做法是将用户加入docker组:

sudo usermod -aG docker $USER
newgrp docker  # 立即生效无需重新登录

重要安全提示:docker组实际上等同于root权限,因此仅可信任用户应被加入该组。生产环境中建议结合SELinux/AppArmor使用

5.2 权限问题排查

如果仍遇到"Got permission denied"错误,按以下步骤排查:

  1. 确认用户是否在docker组:
    groups $USER
    
  2. 检查/var/run/docker.sock权限:
    ls -l /var/run/docker.sock
    
    正确权限应为:
    srw-rw---- 1 root docker 0 Jul 10 10:30 /var/run/docker.sock
    
  3. 若权限不符,修正命令:
    sudo chown root:docker /var/run/docker.sock
    sudo chmod 660 /var/run/docker.sock
    

6. 国内用户特别优化

6.1 镜像加速配置

创建或修改/etc/docker/daemon.json:

sudo tee /etc/docker/daemon.json <<-'EOF'
{
  "registry-mirrors": [
    "https://registry.docker-cn.com",
    "https://hub-mirror.c.163.com",
    "https://mirror.baidubce.com"
  ],
  "exec-opts": ["native.cgroupdriver=systemd"],
  "log-driver": "json-file",
  "log-opts": {
    "max-size": "100m"
  },
  "storage-driver": "overlay2"
}
EOF

配置说明:

  • registry-mirrors :按地理位置选择最优镜像源
  • native.cgroupdriver :与systemd更好的集成
  • log-opts :防止日志文件无限增长
  • storage-driver :Ubuntu 20.04推荐使用overlay2

应用配置并重启服务:

sudo systemctl daemon-reload
sudo systemctl restart docker

6.2 网络问题排查

如果遇到镜像拉取超时,可以:

  1. 测试镜像服务器连通性:
    curl -I https://registry-1.docker.io/v2/
    
  2. 临时使用HTTP代理(如有):
    mkdir -p ~/.docker
    echo '{"proxies":{"default":{"httpProxy":"http://proxy.example.com:8080","httpsProxy":"http://proxy.example.com:8080"}}}' > ~/.docker/config.json
    

7. 生产环境关键配置

7.1 存储驱动选择

Ubuntu 20.04默认使用overlay2驱动,但应根据工作负载特点选择:

驱动类型 适用场景 优点 缺点
overlay2 大多数场景 性能好,支持共享层 需要内核≥4.0
aufs 旧系统兼容 稳定性高 已弃用,性能较差
devicemapper 直接块设备 隔离性强 配置复杂,需要LVM

检查当前驱动:

docker info | grep "Storage Driver"

7.2 日志与数据管理

防止Docker占用所有磁盘空间:

sudo tee /etc/docker/daemon.json <<-'EOF'
{
  "data-root": "/mnt/docker-data",
  "log-opts": {
    "max-size": "50m",
    "max-file": "3"
  }
}
EOF

然后迁移现有数据:

sudo systemctl stop docker
sudo rsync -a /var/lib/docker/ /mnt/docker-data/
sudo mv /var/lib/docker /var/lib/docker.bak
sudo systemctl start docker

8. 常见问题解决方案

8.1 启动失败排查

如果遇到"Failed to start Docker Application Container Engine":

  1. 查看完整日志:
    journalctl -xu docker --no-pager
    
  2. 常见错误及修复:
    • iptables缺失 sudo apt install iptables
    • cgroup挂载问题 :在/etc/default/grub中添加 systemd.unified_cgroup_hierarchy=0 sudo update-grub
    • 存储驱动冲突 :清理/var/lib/docker后重新安装

8.2 容器网络异常

典型症状:容器内无法访问外网

解决步骤:

  1. 检查DNS配置:
    docker run --rm busybox nslookup example.com
    
  2. 重置Docker网络:
    sudo systemctl restart docker
    docker network prune
    
  3. 检查iptables规则:
    sudo iptables -L -n -v --line-numbers
    

9. 进阶配置建议

9.1 安全加固措施

  1. 启用用户命名空间隔离:

    echo "dockremap:165536:65536" | sudo tee -a /etc/subuid
    echo "dockremap:165536:65536" | sudo tee -a /etc/subgid
    

    然后在daemon.json中添加:

    {
      "userns-remap": "dockremap"
    }
    
  2. 限制容器权限:

    docker run --read-only --security-opt="no-new-privileges" -it alpine sh
    

9.2 性能调优参数

在/etc/sysctl.conf中添加:

# 增加连接跟踪表大小
net.netfilter.nf_conntrack_max = 524288

# 优化网络性能
net.core.rmem_max = 16777216
net.core.wmem_max = 16777216
net.ipv4.tcp_keepalive_time = 600

# 容器专用配置
fs.inotify.max_user_instances = 8192
fs.inotify.max_user_watches = 524288
vm.swappiness = 10

应用配置: sudo sysctl -p

10. 维护与升级策略

10.1 定期维护任务

  1. 清理无用资源:
    docker system prune -af --volumes
    
  2. 检查容器健康状态:
    docker stats --all --format "table {{.Name}}\t{{.CPUPerc}}\t{{.MemUsage}}"
    
  3. 备份关键数据:
    tar -czvf docker-backup-$(date +%Y%m%d).tar.gz /mnt/docker-data/
    

10.2 版本升级方案

  1. 查看可用版本:
    apt-cache madison docker-ce
    
  2. 测试环境验证:
    sudo apt install docker-ce=<新版本> docker-ce-cli=<新版本>
    
  3. 滚动升级策略:
    • 先升级控制节点
    • 逐个节点排空(drain)后升级
    • 使用蓝绿部署减少停机时间

我在生产环境中发现,直接apt upgrade docker-ce有时会导致容器网络中断。更稳妥的做法是:

  1. 提前排空节点
  2. 停止所有容器
  3. 执行版本升级
  4. 重启dockerd服务
  5. 恢复容器运行

更多推荐