1. 项目概述:为什么需要离线安装Docker?

在Linux服务器运维和项目部署的日常工作中,我们常常会遇到一个看似简单却颇为棘手的问题:生产环境或内网服务器无法连接互联网。无论是出于安全策略的硬性规定,还是机房物理隔离的客观条件,这些服务器都处于“离线”状态。此时,如果你需要部署一套基于容器化的应用,比如一个微服务项目,或者一个数据采集系统,安装Docker就成了第一道坎。

“离线安装Docker”这个需求,正是为了解决这个核心矛盾。它不是一个简单的“下载安装包”的过程,而是一个涉及依赖分析、版本匹配、环境准备和手动配置的系统性工程。很多新手运维或者开发者在第一次面对这个问题时,往往会感到无从下手,要么是下载的包版本不对,要么是依赖缺失导致安装失败,要么是安装后服务无法启动。我自己在早期也踩过不少坑,比如在CentOS 7上费劲下载了一堆RPM包,结果因为glibc版本不匹配而前功尽弃。

所以,这篇文章的目的,就是为你梳理出一套清晰、可靠、可复现的Linux环境离线安装Docker的完整方案。我会从原理讲起,告诉你离线安装的本质是什么,然后手把手带你完成从准备离线包到最终验证的每一个步骤,并分享我积累下来的那些“血泪教训”和避坑技巧。无论你面对的是CentOS、Ubuntu还是其他主流的Linux发行版,这套思路都是通用的。

2. 核心原理与准备工作拆解

2.1 理解离线安装的本质:依赖链的本地化

在线安装之所以简单,是因为包管理器(如 yum apt )帮我们自动解决了依赖关系。你只需要一个命令,它就会从配置好的镜像源拉取Docker安装包及其所有依赖包。而离线安装,就是把这个“拉取”的动作提前,在能联网的机器上模拟一次完整的安装过程,把所有需要的文件(主包、依赖包、配置文件)全部下载到本地,然后打包转移到目标离线服务器上,再通过本地路径进行安装。

这个过程的关键在于 依赖的完整性 。Docker CE(社区版)的依赖可能包括:

  • 容器运行时 :如 containerd.io ,这是Docker的核心组件之一,负责管理容器的生命周期。
  • Docker引擎 docker-ce 本身。
  • 命令行工具 docker-ce-cli
  • 系统依赖 :如 libseccomp (安全计算模式库)、特定版本的 systemd iptables 等。

不同的Linux发行版和版本,其软件包格式和依赖树完全不同。例如,CentOS/RHEL及其衍生版(如Rocky Linux、AlmaLinux)使用RPM包,而Debian/Ubuntu使用DEB包。这是准备工作前必须明确的第一点。

2.2 环境侦察与工具选型

在开始之前,你必须像侦察兵一样摸清“敌情”。这包括:

  1. 目标服务器信息确认

    • 操作系统及版本 :执行 cat /etc/os-release lsb_release -a 查看。例如,是 CentOS Linux 7.9 还是 Ubuntu 22.04 LTS
    • 系统架构 :执行 uname -m 查看。最常见的是 x86_64 (即AMD64),也可能是 aarch64 (ARM架构,常见于国产化环境或树莓派)。
    • 内核版本 :Docker对内核有要求(一般3.10以上),执行 uname -r 查看。虽然离线包不直接依赖内核包,但确保内核支持是前提。
  2. 准备一台同构的联网跳板机

    • 这是整个流程的基石。你需要一台 能够连接互联网 ,并且 操作系统发行版、主版本号、系统架构与目标离线服务器完全一致 的机器。例如,目标机是CentOS 7.9 x86_64,跳板机也必须是CentOS 7.9 x86_64。这是保证下载的软件包100%兼容的关键。用虚拟机临时搭建一个是最稳妥的办法。
  3. 选择Docker版本

    • 访问Docker官方文档,确定一个稳定、兼容的版本。对于生产环境,不建议使用最新的 edge 版本,而是选择一个经过考验的稳定版。例如,在写这篇文章时, 20.10.x 24.0.x 系列都是不错的选择。你可以通过 yum list docker-ce --showduplicates (联网环境下)来查看所有可用版本。

注意 :版本选择上有个小技巧,如果你的应用对Docker版本有特定要求(例如某些旧版编排工具),那就遵循应用要求;如果没有,选择比最新稳定版稍旧一个次版本的版本,通常社区里遇到的坑和解决方案会更多,更稳妥。

3. 实战演练:分步构建离线安装包

接下来,我们以 CentOS 7.x x86_64 系统为例,演示完整的离线包制作与安装过程。Ubuntu/Debian系的思路完全一致,只是包管理命令从 yum 换成了 apt

3.1 阶段一:在联网跳板机上操作

这个阶段的目标是创建一个包含所有必要文件的离线包。

3.1.1 环境初始化与仓库配置

首先,在跳板机上清理旧Docker版本(如果有),并添加Docker官方CE仓库。

# 1. 卸载旧版本(如果存在)
sudo yum remove docker \
                  docker-client \
                  docker-client-latest \
                  docker-common \
                  docker-latest \
                  docker-latest-logrotate \
                  docker-logrotate \
                  docker-engine

# 2. 安装yum工具集,`yum-utils` 提供了 `yumdownloader` 这个关键工具
sudo yum install -y yum-utils

# 3. 添加Docker官方CE仓库
sudo yum-config-manager \
    --add-repo \
    https://download.docker.com/linux/centos/docker-ce.repo
3.1.2 下载Docker及其所有依赖

这是核心步骤。我们使用 yumdownloader 命令,它不仅能下载指定的RPM包,还能通过 --resolve 参数自动下载所有依赖。

# 创建一个目录来存放所有下载的包
mkdir -p /opt/docker-offline-packages
cd /opt/docker-offline-packages

# 使用 yumdownloader 下载指定版本的docker-ce, docker-ce-cli, containerd.io 及其所有依赖
# 假设我们选择安装 docker-ce-20.10.24
sudo yumdownloader --resolve docker-ce-20.10.24 docker-ce-cli-20.10.24 containerd.io

执行完上述命令后,当前目录下会多出几十个 .rpm 文件。这些就是Docker运行所需的所有软件包。

实操心得 yumdownloader 默认会下载当前仓库中最新版本的包。如果你不指定版本,比如只写 docker-ce ,那么下载的就是最新的。在生产环境中, 强烈建议指定具体版本号 ,这样可以确保离线环境和后续扩容环境的一致性,避免因版本差异导致不可预知的问题。

3.1.3 额外关键:下载 device-mapper-persistent-data lvm2

对于CentOS/RHEL 7,Docker默认的存储驱动曾经是 devicemapper ,虽然新版本默认已改为 overlay2 ,但一些旧指南或系统可能仍需要这些依赖。为了确保万无一失,特别是如果你不确定目标服务器的历史配置,最好一并下载。

sudo yumdownloader --resolve device-mapper-persistent-data lvm2
3.1.4 打包与完整性校验

下载完成后,我们需要将这些包和安装脚本一起打包,方便传输。

# 回到上级目录,准备打包
cd /opt

# 创建一个简单的安装脚本模板(稍后会在目标服务器上编辑)
cat > install-docker.sh << 'EOF'
#!/bin/bash
# 离线安装Docker脚本
# 请将此脚本与所有.rpm文件放在同一目录下执行

INSTALL_DIR=$(dirname "$0")
cd $INSTALL_DIR

echo “开始安装Docker离线包...”
# 使用本地路径安装所有rpm包,忽略依赖检查(因为依赖包已全部在本地)
sudo rpm -ivh --nodeps *.rpm

echo “启动Docker服务并设置开机自启”
sudo systemctl start docker
sudo systemctl enable docker

echo “验证安装”
sudo docker --version
EOF

# 给脚本添加执行权限
chmod +x docker-offline-packages/install-docker.sh

# 打包整个目录
tar -czvf docker-offline-20.10.24-centos7.x86_64.tar.gz docker-offline-packages/

现在, docker-offline-20.10.24-centos7.x86_64.tar.gz 这个文件就是我们的终极离线安装包。你可以通过U盘、内网FTP、或者安全的文件传输工具将其复制到目标离线服务器。

3.2 阶段二:在目标离线服务器上操作

将上一步生成的压缩包上传到目标服务器的某个目录,例如 /tmp

3.2.1 解压与预检查
# 1. 切换到上传目录并解压
cd /tmp
tar -xzvf docker-offline-20.10.24-centos7.x86_64.tar.gz

# 2. 进入解压后的目录
cd docker-offline-packages

# 3. (可选但推荐)手动检查内核是否支持overlay2存储驱动
# 这是Docker推荐且性能更好的存储驱动
lsmod | grep overlay
# 如果没有任何输出,需要加载模块
sudo modprobe overlay
# 确认加载成功
lsmod | grep overlay
3.2.2 执行离线安装

直接运行我们准备好的脚本,或者手动执行安装命令。

方法一:使用脚本(推荐)

sudo ./install-docker.sh

脚本会依次安装所有RPM包,启动Docker服务并设置开机自启。

方法二:手动安装 如果你想更清晰地控制过程,可以手动执行:

# 安装所有rpm包
sudo rpm -ivh --nodeps *.rpm

# 启动并设置开机自启
sudo systemctl start docker
sudo systemctl enable docker

关键参数解释 rpm -ivh --nodeps 中的 --nodeps 参数表示“不检查依赖”。这是因为我们在跳板机上下载时,已经通过 --resolve 确保了所有依赖包都在当前目录。如果不用这个参数, rpm 命令会去线上仓库查找依赖,在离线环境下必然会失败。

3.2.3 安装后配置与验证

安装完成后,有几项重要的后续工作。

  1. 验证安装

    sudo docker --version
    # 预期输出:Docker version 20.10.24, build 297e128
    sudo systemctl status docker
    # 查看服务状态,应为 active (running)
    
  2. 配置用户组(非root用户运行Docker) : 默认情况下,执行Docker命令需要 sudo 。为了方便,可以将当前用户加入 docker 用户组。

    sudo groupadd docker  # 如果docker组不存在则创建,通常安装时会自动创建
    sudo usermod -aG docker $USER
    

    重要 :执行此命令后,需要 完全注销并重新登录 ,或者新开一个终端,用户组更改才会生效。之后,你就可以直接使用 docker ps 而不需要 sudo 了。

  3. 测试Docker基础功能

    # 运行一个最简单的测试容器
    docker run hello-world
    

    如果这个命令能成功执行,并输出 “Hello from Docker!” 等欢迎信息,那么恭喜你,Docker离线安装已经大功告成。

4. 针对不同发行版的策略调整

虽然我们以CentOS为例,但其他发行版的流程大同小异,核心是更换包管理工具。

4.1 Ubuntu/Debian 系统

在Ubuntu跳板机上的操作流程对比如下:

步骤 CentOS/RHEL系 Ubuntu/Debian系
安装下载工具 yum install yum-utils apt install dpkg-dev (或使用 apt-offline )
添加仓库 yum-config-manager --add-repo add-apt-repository 或手动编辑 /etc/apt/sources.list.d/docker.list
下载包及依赖 yumdownloader --resolve apt download <package> 配合 apt-cache depends 手动解析,或使用 apt-offline 更佳
本地安装命令 rpm -ivh --nodeps *.rpm dpkg -i *.deb

对于Ubuntu,更推荐使用 apt-offline 工具,它能更优雅地生成一个完整的离线安装签名文件( sig 文件),在目标机上用这个文件来获取所有包。但考虑到通用性,手动下载依赖也是一种可行方案,只是过程更繁琐一些。

4.2 国产化操作系统(如麒麟、统信UOS)

国产系统大多基于CentOS或Ubuntu的某个版本衍生。首先,使用 cat /etc/os-release 命令,找到其“基系统”信息。例如,银河麒麟V10可能基于CentOS 8。然后,按照对应的基系统(CentOS或Ubuntu)的离线安装方法进行。 关键点 在于,Docker官方可能不直接提供该衍生版的仓库,你需要:

  1. 确认系统自带的仓库或第三方兼容仓库中是否有Docker包。
  2. 如果没有,尝试使用其基系统对应版本的Docker包(如CentOS 8的包用于麒麟V10),但这存在一定的兼容性风险,务必先在测试环境验证。

5. 高级技巧与深度避坑指南

5.1 存储驱动选择与配置

安装完成后,Docker默认使用的存储驱动未必是最优的。对于CentOS/RHEL 7,如果内核版本 >= 3.10,且文件系统是 xfs 并启用了 ftype=1 ,强烈建议使用 overlay2 驱动。

检查并配置overlay2

# 1. 检查当前存储驱动
docker info | grep “Storage Driver”

# 2. 如果显示为 devicemapper,建议修改为 overlay2
# 停止Docker服务
sudo systemctl stop docker

# 编辑Docker守护进程配置文件
sudo vi /etc/docker/daemon.json

daemon.json 文件中添加以下内容(如果文件不存在则创建):

{
  “storage-driver”: “overlay2”
}

保存后,启动Docker: sudo systemctl start docker 。再次使用 docker info 确认驱动已更改。

踩坑记录 :我曾遇到一个环境,修改为 overlay2 后Docker启动失败。原因是 /var/lib/docker 目录下存在旧的 devicemapper 数据。解决方法是在修改配置前,先备份并 清理 /var/lib/docker 目录( sudo rm -rf /var/lib/docker/* )。这是一个危险操作,仅适用于全新安装或可接受数据丢失的环境,生产环境务必谨慎!

5.2 离线环境下的镜像管理

Docker安装好了,但怎么在没有网络的环境下获取镜像呢?答案是: 镜像导出与导入

  1. 在联网机器上拉取并保存镜像

    docker pull nginx:alpine
    docker save -o nginx-alpine.tar nginx:alpine
    
  2. nginx-alpine.tar 文件拷贝到离线服务器

  3. 在离线服务器上加载镜像

    docker load -i nginx-alpine.tar
    
  4. 验证

    docker images
    docker run -d -p 80:80 nginx:alpine
    

对于复杂的多镜像应用(例如包含web、app、db多个服务的Compose项目),你需要在联网环境将每个镜像都 save 出来,然后到离线环境逐个 load 。也可以使用脚本批量操作。

5.3 常见问题排查实录

即使按照步骤操作,也可能遇到意外。下面是我总结的几个典型问题及解决方案。

问题现象 可能原因 排查与解决思路
rpm -ivh 安装时报错,提示文件冲突 系统中已存在旧版本或冲突的软件包。 使用 `rpm -qa
systemctl start docker 失败,查看日志 journalctl -xe -u docker 发现 ”Failed to start Docker Application Container Engine.” 1. 存储驱动配置错误(如上述overlay2问题)。
2. 内核模块未加载(如 overlay br_netfilter )。
3. 防火墙或SELinux阻止。
1. 检查 /etc/docker/daemon.json 配置。
2. 执行 sudo modprobe overlay sudo modprobe br_netfilter 手动加载模块,并确保开机自动加载(写入 /etc/modules-load.d/ )。
3. 临时关闭防火墙和SELinux测试: sudo setenforce 0 sudo systemctl stop firewalld 。如果是它们的问题,需要配置放行规则而非简单关闭。
执行 docker run hello-world 时提示 ”Cannot connect to the Docker daemon…” Docker服务未启动,或当前用户没有权限连接Docker socket。 1. 确认服务状态: systemctl status docker
2. 确认当前用户是否在 docker 组内: groups $USER 。如果不在,执行 sudo usermod -aG docker $USER 重新登录
在国产化系统上安装后,运行容器性能极差或报错 内核兼容性问题,或缺少必要的内核特性支持。 1. 检查内核版本和发行版说明,确认官方是否支持该环境。
2. 考虑使用更轻量级的容器方案,如 Podman(其命令行与Docker高度兼容),并寻找对应的离线安装方案。

5.4 构建企业级离线镜像仓库

对于需要长期在离线环境部署多个项目的团队,每次都手动 save/load 镜像效率太低。更专业的做法是搭建一个 私有的离线Docker镜像仓库

  1. 在联网环境 :拉取所有需要的镜像,并推送到一个你自己搭建的私有仓库(如使用 registry:2 镜像)。
  2. 将整个私有仓库的数据目录(通常是 /var/lib/registry )打包
  3. 在离线环境 :部署同样的私有仓库容器,并将打包的数据目录解压覆盖。
  4. 配置离线环境的Docker客户端 ,将其镜像仓库地址指向这个内网私有仓库地址(通过修改 /etc/docker/daemon.json 中的 ”insecure-registries” )。

这样,离线环境中的所有机器都可以从这个内网仓库拉取镜像,实现了镜像的集中管理和高效分发。这算是离线Docker使用的进阶玩法了,能极大提升运维效率。

更多推荐