Ubuntu服务器上安装Docker与Docker Compose的完整流程与排错指南

发布时间:2026/9/20 19:41:43

Ubuntu服务器上安装Docker与Docker Compose的完整流程与排错指南 每次新装一台 Ubuntu 服务器我要做的第一件事几乎都是装 Docker。不管是部署个人项目、跑中间件做测试还是搭建一套完整的主机运维环境Docker 和 docker-compose 基本是绕不开的两件套。这个标题看起来简单但实际操作里踩坑的点不少比如 GPG 密钥失效、apt 源拉取超时、docker-compose 版本不匹配、普通用户权限不足等等。这篇文章就把我平时在 Ubuntu 上从零装好这两个工具的全过程、选型思路和排错记录完整梳理一遍给你一份可以直接照着抄的作业。文章内容适合刚接触 Linux 和容器的小白也适合已经装过但想换个更规范方式重新搭建的老手。我会把每一步背后的原理和判断逻辑也讲清楚不是光给命令而是让你知道为什么这样做、遇到问题该往哪个方向排查。1. 装之前先把这些概念和前提理清楚1.1 Docker Engine 和 docker-compose 分别是什么Docker Engine 是容器运行时的核心它负责拉取镜像、创建容器、管理网络和存储卷是真正干活的那一层。平时我们说“装 Docker”指的就是在服务器上安装并运行 Docker Engine装完之后通过docker命令来操作容器。docker-compose 则是用来定义和运行多容器应用的工具。你可以在一个 YAML 文件里写清楚需要哪几个服务、每个服务用什么镜像、端口怎么映射、依赖关系怎么处理然后一条docker compose up -d命令就能把整套环境拉起来。对于跑 MySQL、Redis、Nginx 这类常见组合docker-compose 要比手动敲一长串docker run参数省心得多。需要特别说明一点从 Docker Compose v2 开始官方推荐的方式是以 Docker 插件的形式使用命令也从原来的docker-compose带横杠变成了docker compose空格。目前主流的安装方式和网上绝大多数教程都已经向 v2 迁移下面的步骤也会以 v2 插件版为主同时说明独立二进制方式的用法。1.2 为什么首选付费少、资料全的 Ubuntu LTS 版本Ubuntu 的 LTS 版本如 20.04、22.04、24.04拥有长达五年的安全更新支持Docker 官方对 LTS 版本的适配和测试也最充分。如果你的服务器是生产环境优先选择 24.04 LTS 这类长期支持版本不仅稳定遇到问题时能搜到的解决方案也最多。这篇文章以 Ubuntu 24.04 LTS 为例演示不过对于 20.04、22.04 这些版本安装命令和步骤基本一致区别只在部分依赖包的名称可能有细微不同。我实际测试下来这三代 LTS 系统的安装流程完全通用。1.3 安装前检查系统内核版本和残留的旧包Docker 对 Linux 内核有最低版本要求一般是 3.10 以上。Ubuntu 20.04 及之后版本的内核都远高于这个线所以基本不用操心内核问题。不过还是建议先确认一下系统信息避免后续出现莫名其妙的问题# 查看系统版本信息 lsb_release -a # 查看当前内核版本 uname -r另外要检查系统里是否已经安装过旧版 Docker 相关软件包。如果你之前用apt install docker或apt install docker.io装过直接再装 Docker Engine 会冲突。先确认一下现状# 列出已安装的docker相关包 dpkg -l | grep -i docker如果有类似docker.io、docker-engine、containerd、runc的旧包先卸载干净再开始。注意这里说的是系统自带或手动安装的旧版本如果以前装过 Docker 官方源里的版本完全卸载后直接升级即可。不清理干净的话后面启动服务时可能出现端口占用、启动失败的状况。2. 安装 Docker Engine 的完整流程2.1 为什么我推荐走 Docker 官方 apt 仓库安装安装 Docker Engine 有三种主流方式。第一种是直接用apt install docker.io这是 Ubuntu 软件源里自带的版本。优点是一条命令搞定省事缺点是版本往往偏老而且没有 Docker 官方仓库的更新及时。对于追求稳定和懒人而言也不是不能用但新特性、安全补丁的获取会滞后。第二种是 Docker 官方提供的便捷安装脚本执行curl -fsSL https://get.docker.com | sh即可。优点是真的方便脚本会自动检测系统、配置源并安装最新版缺点是脚本做了一些自动化操作你不好控制每一步的细节如果公司或学校网络有代理要求处理起来反而麻烦。第三种就是我推荐的方式手动添加 Docker 官方 apt 源再用apt install docker-ce docker-ce-cli containerd.io安装。这样既能确保拿到官方最新版本也能清楚了解每个步骤在做什么后续升级只需apt update apt upgrade即可。2.2 添加 Docker 官方源并安装 gpg 密钥的细节点先更新本地的软件包索引并安装几个后续会用到的工具包sudo apt update sudo apt install -y ca-certificates curl gnupg lsb-release这里面的ca-certificates是为了让系统信任 HTTPS 证书curl用来下载密钥gnupg用来处理密钥验证lsb-release则用于识别当前系统的发行版代号。接下来创建密钥目录并下载 Docker 官方的 GPG 密钥。我在实际运维中发现这一步很多人会漏掉install -m 0755 -d这个细节直接随便建目录导致权限不对。标准的做法是sudo install -m 0755 -d /etc/apt/keyrings curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo gpg --dearmor -o /etc/apt/keyrings/docker.gpg sudo chmod ar /etc/apt/keyrings/docker.gpg这条命令把 Docker 官方公钥下载后做了一次 dearmor 转换转换成二进制格式存到/etc/apt/keyrings/docker.gpg。之后的chmod ar是为了让所有用户都能读取密钥避免后续 apt 更新时出现权限报错。然后添加 Docker 的 apt 仓库。注意这里的写法官方文档里使用了一种根据系统架构和版本号动态生成路径的方式自动适配 Ubuntu 的 codenameecho \ deb [arch$(dpkg --print-architecture) signed-by/etc/apt/keyrings/docker.gpg] https://download.docker.com/linux/ubuntu \ $(lsb_release -cs) stable | sudo tee /etc/apt/sources.list.d/docker.list /dev/nulldpkg --print-architecture会自动输出当前系统的 CPU 架构通常是 amd64 或 arm64lsb_release -cs会输出 Ubuntu 的代号如 noble、jammy、focal。这样写的好处是一段命令在任何 Ubuntu 版本上都能正确生成对应的源地址。2.3 安装 docker-ce 并验证服务状态添好仓库后先执行sudo apt update让系统识别新仓库。如果之前没有配置过 Docker 源这一步可能会提示Get:... docker.list之类的信息说明仓库已经成功加载。然后安装三个核心组件sudo apt update sudo apt install -y docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-plugin我这边把docker-buildx-plugin和docker-compose-plugin也一并安装了。buildx 是 Docker 官方推出的多平台镜像构建插件docker compose子命令则依赖docker-compose-plugin这个包。一次装齐后面不用再折腾。安装完成后启动 Docker 服务并设为开机自启sudo systemctl enable docker sudo systemctl start docker用systemctl status docker可以看服务状态一个绿色的 active (running) 就代表正常。最后跑一遍经典的验证命令sudo docker run hello-world如果能看到 Hello from Docker! 的输出说明整个 Docker Engine 已经正常工作能拉取镜像、创建并运行容器。3. 安装 docker-compose 的两种方式和版本选择3.1 直接使用官方插件一条命令省心省事之前装 Docker 时如果一并安装了docker-compose-plugin那现在直接就能用docker compose了。验证方式docker compose version输出如Docker Compose version v2.24.0即正常。这种方式的优点是随 Docker Engine 一起升级版本由 apt 统一管理不需要关心独立二进制的安装路径、权限问题命令调用速度也更快毕竟少了一层解释执行日常使用中docker compose up -d、docker compose logs -f、docker compose down这些命令都直接在项目目录下敲就行。网上很多旧教程会让你去 GitHub 下载docker-compose-linux-x86_64二进制文件并放到/usr/local/bin。这个方案也没错但独立二进制方式有两个明显的缺点一是需要手动跟进版本GitHub 上新版本发布后系统的 apt 永远不会帮你升级二是和 Docker Engine 的 version 匹配偶尔会出问题Compose 版本太旧时某些新特性如 profiles 多环境配置会提示不支持。我的建议很明确如果是 2023 年以后装的系统默认就走插件方式不要再折腾独立二进制。除非你有特殊需求比如需要在 CI/CD 流水线里指定特定版本号的docker-compose可执行文件。3.2 坚持要独立二进制的话按住这几个关键点来假设你就是想在系统里保留一个传统风格的docker-compose命令操作路径如下。先去 GitHub 的 docker/compose 仓库 Releases 页面查看最新的版本号。以 v2.29.1 为例sudo curl -L https://github.com/docker/compose/releases/download/v2.29.1/docker-compose-$(uname -s)-$(uname -m) -o /usr/local/bin/docker-composeuname -s会输出 Linuxuname -m会输出 x86_64 或 aarch64自动匹配正确的包名。下载完成后需要给执行权限sudo chmod x /usr/local/bin/docker-compose验证是否成功docker-compose --version需要升级时直接重复一遍覆盖下载的过程替换版本号即可。删除时删掉/usr/local/bin/docker-compose这个文件就行。还要留意一个坑独立二进制版默认不在docker compose的 PATH 搜索范围内它和插件版的docker compose是两条平行的命令二者并不互相感知。我不建议同一台机器上同时装插件版和独立二进制版容易混淆也会让后续维护脚本的人困惑到底用的是哪一份配置。3.3 版本选择策略到底该追新还是求稳不管走插件还是独立二进制都会遇到版本选择的问题。插件版的版本由 Docker Engine 的 apt 源决定默认给你装的就是官方仓库中的最新稳定版基本不需要自己指定。如果你真的需要锁定版本可以先用apt-cache policy docker-compose-plugin查看可用版本再通过sudo apt install docker-compose-plugin版本号来指定。独立二进制版则可以随意选择。根据我的经验生产环境优先选择最近半年内发布的稳定版不要一上来就追刚出的版本也没必要执着于最新版。开发测试环境直接用最新版问题不大。如果现有项目里的 docker-compose.yml 是好几年前写的遇到语法报错时优先检查 Compose 版本和格式声明是否匹配不要急着骂写文件的人。Compose 规范版本有 v2、v3 的区别部分字段在不同版本间有兼容性差异。4. 装完之后的三个基础配置建议顺手做掉4.1 把当前用户加入 docker 组省掉每次敲 sudo默认情况下执行docker命令需要 root 权限否则会报permission denied trying to connect to the docker daemon socket。这个设计是出于安全考虑因为能操作 Docker 的用户基本等同于能操作整个主机。不过对于个人开发机每次都打 sudo 实在太繁琐。标准做法是把用户加入docker用户组sudo usermod -aG docker $USER然后注销重新登录或者执行newgrp docker使组权限立即生效。之后直接运行docker ps不再需要 sudo。这里有个安全提示真的值得多说一句把用户加入 docker 组等价于授予该用户 root 权限因为可以通过挂载主机目录等方式完全控制宿主机。如果你配置的是多人共用的服务器不要轻易给不信任的账号加 docker 组权限。4.2 镜像拉取慢的通用解决思路配置 registry mirror很多人在 Ubuntu 上装完 Docker 后第一个明显的痛点就是“镜像下载慢”。这个问题在国内网络环境下尤为突出拉一个几百 MB 的镜像可能要等上几分钟甚至超时。常规的解决办法是给 Docker 配置镜像加速器也就是 registry mirror。Docker 官方文档中registry mirror 的作用是让 Docker 守护进程先从配置的镜像源拉取镜像如果目标仓库有缓存就能明显加速。需要注意的是镜像加速器通常只覆盖 Docker Hub 上的公共镜像拉取 ghcr.io、quay.io 这类第三方仓库里的镜像时不会生效。配置步骤如下sudo mkdir -p /etc/docker sudo tee /etc/docker/daemon.json EOF { registry-mirrors: [https://your-mirror-address] } EOF然后重启 Docker 服务sudo systemctl daemon-reload sudo systemctl restart docker关于镜像加速地址的选择我的建议是不要随便找一个来路不明的地址填上去。比较可靠的来源是各云服务商容器镜像服务页面注册后可以获取专属格式的加速地址个人用户免费额度足够开发使用。如果你的服务器本身就在云厂商内网可以直接尝试云厂商提供的默认内网加速域名。改完配置后可以用docker info查看 Registry Mirrors 一栏是否生效再拉一个实际镜像测试速度。4.3 日志上限配置防止磁盘被容器日志塞满容器默认会无限收集标准输出日志如果应用打印信息比较多比如 Nginx 访问日志、Java 应用错误栈时间一长容易把磁盘撑爆。这是我在服务器上踩过最实在的坑之一。推荐在daemon.json中统一设置日志轮转策略{ log-driver: json-file, log-opts: { max-size: 10m, max-file: 3 } }这个配置限制单个容器日志文件最大 10MB最多保留 3 份超出后自动滚动清理。设置完成后重启 Docker 服务再创建容器时生效旧容器如果在创建时显式指定了 log 参数则不受全局配置影响。5. 常见问题与排查实录5.1 权限类问题docker 命令报权限不足报错示例docker: permission denied while trying to connect to the Docker daemon socket at unix:///var/run/docker.sock排查思路分两步。第一步确认 Docker 服务是否正常运行systemctl status docker如果服务没跑起来先sudo systemctl start docker再试。服务正常运行却报权限不足那就是当前用户在 docker 组的问题。groups $USER sudo usermod -aG docker $USER修改组之后务必要重新登录终端或执行newgrp docker否则当前会话里组信息不会刷新。5.2 网络与密钥问题apt update 卡住或密钥报错添加 Docker 官方仓库后执行sudo apt update有时会出现两种情况。一是仓库地址连接超时卡在一个百分数不动。这种通常是服务器到 download.docker.com 的网络链路不稳定。可以尝试切换到 mirror 地址。网络上常见的做法是更换成适合自己网络环境的 Docker 镜像站来做为 apt 源但这样做的代价是更新不及时而且来源可靠性需要你自己判断。我的建议是先多试几次再看是不是系统代理配置的问题。如果服务器有 HTTP 代理apt 默认不读http_proxy环境变量需要在/etc/apt/apt.conf.d/下配置Acquire::http::Proxy。二是密钥相关报错The following signatures couldnt be verified because the public key is not available: NO_PUBKEY xxxxx这种多半是因为/etc/apt/keyrings/docker.gpg没有正确读取。先确认文件是否存在、权限是否能被 apt 读取。可以用sudo chmod ar /etc/apt/keyrings/docker.gpg强制修正。如果还是不行重新执行一遍下载密钥的命令即可。5.3 验证阶段报错hello-world 镜像拉不下来执行sudo docker run hello-world时卡在 Pulling 阶段或者报timeout、TLS handshake timeout之类的错误原因基本都是 Docker Hub 的默认仓库连接不畅。解决办法就是参照 4.2 的 registry mirror 配置配好镜像加速地址后重启 Docker 再试。如果改完依然超时可以用docker pull hello-world单独拉一次看具体报错然后再逐项排查 DNS、防火墙、代理等。另外我还遇到过一种情况daemon.json格式写错了比如多了一个逗号Docker 服务直接启动失败。排查时可以查看 Docker 服务日志sudo journalctl -u docker -n 50如果输出里提示 daemon.json 解析错误修正 JSON 格式后重启即可。5.4 版本不兼容docker-compose.yml 格式报错有时从网上复制了一份 docker-compose.yml执行docker compose up -d时直接报错services.web Additional property xxx is not allowed这种大概率是版本声明和实际 Componse 版本不匹配。Compose 规范在 v2 和 v3 之间废弃了一些字段比如version在较新版本里已经不再推荐显式声明。遇到这种问题我一般处理方式是先把文件顶部的version:字段去掉因为 Compose 插件会根据命令推断格式如果还报错就逐行检查出错的 service 字段是否拼写正确特别是缩进YAML 对空格非常敏感。调试时可以用docker compose config来校验文件语法这条命令会解析整个 Compose 文件并输出最终配置不启动任何容器是排查格式问题最好的工具。如果不输出内容说明docker-compose.yml没有问题。5.5 一个容易被忽略的点重启系统后 Docker 服务消失如果你装了 Docker 之后没有执行过systemctl enable docker重启机器后 Docker 服务不会自动启动届时所有容器都会变成“停止”状态。这个问题在新手环境里非常常见。装好之后我总会先确认 enable 状态sudo systemctl is-enabled docker输出enabled表示已设置开机自启。如果是disabled执行sudo systemctl enable docker如果容器是通过 docker-compose 部署的等 Docker 启动后还需要docker compose start拉起对应项目中的服务。注意start和up的区别在于start不会读取文件里的构建或映射变更只会启动已存在的容器适合系统重启后的恢复场景up则适合首次部署或配置变更后的更新场景。写在最后的一点个人体会Docker 和 docker-compose 的安装本身其实不难难的是装完之后整个环境是否真正顺手、后续升级维护是否省心。我推荐的方式总结下来就一句话走 Docker 官方 apt 仓库安装最新稳定版 Docker Engine同时带上 compose 插件包装完立刻配上用户组、镜像加速和日志上限三件事。这套组合我在多台 Ubuntu 20.04、22.04、24.04 服务器上验证过既能满足日常开发需求也适合生产环境长期运行。最后再分享一个个人习惯每次安装完 Docker 后我会顺手写一个docker-compose.yml测试文件里面放一个 Nginx 服务和一个 PostgreSQL 服务跑一遍docker compose up -d并确认两个容器都能正常启动。这个动作耗时不到两分钟却能一次性验证网络、镜像源、端口映射、卷挂载、服务健康检查等多个环节是否正常。比起等到真正部署业务时再发现问题这个提前检查的方式能省下很多排查时间。如果你准备装完就投入实际项目强烈建议也做一次这样的快速验证。
延伸阅读

更多相关文章

2026/9/20 19:41:43

中国软件五十年:从硬件附庸到生态领跑

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/9/20 19:41:43

EVT/DVT/PVT:硬件量产的三道生死红线

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/9/20 20:41:47

Hugging Face Trending:Kimi K2.7 Code 权重,TaoToken 拿 Key 后怎么跑

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/9/20 20:41:47

OpenResearch:面向可复现科研的本地优先CLI方法论

1. 项目概述:一个被误读的开源研究协作范式“OpenResearch”这个词最近在开发者社区里频繁冒头,但很多人一看到就下意识联想到某个具体工具、CLI命令或者AI代码助手——比如把orx当成类似codex cli或claude cli那样的终端插件,甚至有人在飞书…

2026/9/20 20:36:47

MAHNOB-HCI多模态数据处理实战:EEG、眼动与视频同步解析

头一次接触MAHNOB-HCI多模态数据集的人,十有八九都会卡在同一个地方:文件下载好了,目录也解压了,可打开一看——脑电是.bdf,眼动是.txt,视频又是.avi,三种格式八竿子打不着,时间轴也…

2026/9/20 0:04:49

GAMP 5 基于风险的计算机化系统验证:软件分类与审计追踪实践

简介:《A Risk-Based Approach to Compliant GxP Computerized Systems》即业内熟知的GAMP 5指南,面向制药企业质量与IT合规人员、验证工程师及计算机化系统管理者,用于解决GxP法规环境下系统合规性难以科学落地的问题。文档以风险管理为主线…

2026/9/20 0:04:49

安全托管MSSP实战:从静态防御到人机协同的攻防运营与应急响应

简介:这份PPT围绕互联网业务安全托管服务展开,面向企业安全负责人、IT运维人员及关注MSSP/MSS选型的读者,重点回应传统安全过度依赖人工、碎片化静态防御难以对抗产业化攻击等痛点。资源共1个pptx文件,包体约30.63MB,以…

2026/9/20 0:04:49

GAMP 5 基于风险的计算机化系统验证:软件分类与审计追踪实践

简介:《A Risk-Based Approach to Compliant GxP Computerized Systems》即业内熟知的GAMP 5指南,面向制药企业质量与IT合规人员、验证工程师及计算机化系统管理者,用于解决GxP法规环境下系统合规性难以科学落地的问题。文档以风险管理为主线…

2026/9/20 0:04:49

安全托管MSSP实战:从静态防御到人机协同的攻防运营与应急响应

简介:这份PPT围绕互联网业务安全托管服务展开,面向企业安全负责人、IT运维人员及关注MSSP/MSS选型的读者,重点回应传统安全过度依赖人工、碎片化静态防御难以对抗产业化攻击等痛点。资源共1个pptx文件,包体约30.63MB,以…

2026/9/20 4:54:47

USB Type-C PCB布局分区设计:电源、高速信号与PD协议全攻略

做硬件这行,Type-C接口算是典型的“看着简单,做起来全坑”的东西。光引脚就24个,高低速信号、电源、控制线全部塞在一个小小的连接器里,如果PCB布局不做规划,打样回来基本就是“插上没反应”、“高速掉线”、“静电一打…

2026/9/20 5:01:23

系统编程学习原型如何补齐稳定性边界

系统编程学习原型如何补齐稳定性边界预算有限时&#xff0c;我先优化明显多余的复制&#xff0c;而不是猜测性地换容器。用借用传递只读数据通常就能减少分配&#xff1a; fn parse(line: &str) -> Result<Item, Error> { /* ... */ }用基准确认热点确实在分配&am…

2026/9/20 5:09:33

雨花区哪家财务公司代理记账比较好?

在雨花区&#xff0c;企业处理财税事务常常面临诸多挑战&#xff0c;选择一家靠谱的财务公司至关重要。湖南巨勤财务管理咨询有限公司就是本地正规实体财税服务机构&#xff0c;深耕本地工商财税行业多年&#xff0c;熟悉当地工商局、税务局最新政策与申报流程。主营公司注册、…

还想了解更多?直接咨询顾问

免费诊断 + 免费方案 + 透明报价。

全国咨询热线400-8866-253
免费获取方案
咨询二维码