## 动手前的准备:你需要什么
在开始使用 Docker Compose 之前,确保你的服务器或本地电脑已经安装了 Docker 引擎(Docker Engine)和 Docker Compose 工具。Docker Compose 在 Docker Desktop 中默认自带,如果你在 Linux 服务器上操作,需要单独安装。
**检查环境指令:**
```bash
docker --version
docker-compose --version
```
如果 `docker-compose` 未找到,请根据你的系统执行以下安装:
```bash
# Linux (curl 方式安装最新版)
sudo curl -L "https://github.com/docker/compose/releases/latest/download/docker-compose-$(uname -s)-$(uname -m)" -o /usr/local/bin/docker-compose
sudo chmod +x /usr/local/bin/docker-compose
```
安装完成后重新执行版本检查,确认成功。
另外再看一点,需要准备一个项目的目录,例如 `~/myapp`,所有 Compose 文件都放在里面。
## 编写 docker-compose.yml:定义多容器服务
Docker Compose 的核心就是一个 YAML 文件,名为 `docker-compose.yml`。在这个文件中,你可以定义多个服务(Service),每个服务对应一个容器。
下面以一个最简单的 Web 应用为例,包含一个 Nginx 前端和一个 Redis 缓存后端。
```yaml
version: '3.8'
services:
web:
image: nginx:latest
ports:
- "8080:80"
volumes:
- ./html:/usr/share/nginx/html
depends_on:
- cache
cache:
image: redis:alpine
ports:
- "6379:6379"
```
**字段说明:**
- `version`:指定 Compose 文件格式版本,3.8 是目前较稳定的版本。
- `services`:定义服务列表,每个服务下面可以设置镜像、端口映射、卷挂载等。
- `web` 服务:使用 Nginx 镜像,将宿主机 8080 端口映射到容器 80,把当前目录下的 `html` 文件夹挂载到 Nginx 文档目录。
- `cache` 服务:使用轻量级的 Redis Alpine 镜像,暴露 6379 端口。
- `depends_on`:声明 web 服务依赖于 cache 服务,启动时会先启动 cache。
写好文件后,在 `~/myapp` 目录下创建一个 `html` 文件夹,里面放一个 `index.html` 用于测试:
```bash
mkdir html
echo "
Hello from Docker Compose!
" > html/index.html
```
## 启动并验证服务
所有文件就绪后,执行以下命令在后台启动所有服务:
```bash
docker-compose up -d
```
`-d` 参数让容器在后台运行。首次执行会下载镜像,稍等片刻。
运行完成后,用以下命令检查容器状态:
```bash
docker-compose ps
```
你应该看到 `web` 和 `cache` 两个服务都是 `Up` 状态。
接着处理通过浏览器访问 `http://服务器IP:8080`(如果是本地就访问 `http://localhost:8080`),如果看到 `Hello from Docker Compose!` 说明 Web 服务成功。
验证 Redis 是否可访问(可选):
```bash
docker-compose exec cache redis-cli ping
```
返回 `PONG` 表示 Redis 正常工作。
## 高频问题与避坑指南
**问题1:执行 docker-compose up 后提示 “Cannot connect to the Docker daemon”?**
解决方法:当前用户没有 docker 权限。执行以下命令将用户加入 docker 组,然后重新登录或重启终端:
```bash
sudo usermod -aG docker $USER
# 然后重新登录或执行 newgrp docker
```
**问题2:端口被占用导致启动失败?**
启动时如果出现 `port is already allocated` 错误,说明宿主机上的 8080 或 6379 已被其他程序占用。可以修改 docker-compose.yml 中的端口映射,例如将 `"8080:80"` 改为 `"8081:80"`。
**问题3:容器启动后立即退出(Exit 状态)?**
使用 `docker-compose logs` 查看日志:
```bash
docker-compose logs web
```
常见原因:卷挂载路径不对、缺少配置文件、镜像本身要求运行命令。例如一些镜像必须提供命令参数,你可以通过 `command` 字段覆盖。
**避坑要点:**
- 不要随意使用 `latest` 标签在生产环境,应明确指定版本如 `nginx:1.25`。
- `depends_on` 只控制启动顺序,不保证服务就绪。如果需要等待 Redis 完全可用才能启动 Web,请配合 `healthcheck` 或使用脚本轮询。
- 敏感信息(如数据库密码)不要明文写在 docker-compose.yml 中,推荐使用环境变量文件 `.env` 或 Docker Secret。
## 扩展:加入环境变量与网络
在实际的云原生场景中,你可能需要定义持久化数据卷(volumes)和自定义网络(networks)。下面是一个更接近生产环境的示例片段:
```yaml
version: '3.8'
services:
app:
image: your-app:latest
environment:
- DB_HOST=db
networks:
- backend
db:
image: postgres:15
volumes:
- pgdata:/var/lib/postgresql/data
networks:
- backend
volumes:
pgdata:
networks:
backend:
driver: bridge
```
使用自定义网络后,服务之间可以通过服务名(如 `db`)直接通信,无需写 IP。
## 这篇内容的关键结论
Docker Compose 是云原生运维中管理多容器应用的核心工具。本文从零开始,带你安装了环境、编写了第一个 docker-compose.yml、启动了服务并做了验证,同时指出了常见的坑和解决方案。当你把这套流程跑通之后,后续只需要修改 YAML 文件中的镜像和配置,就能快速部署自己的应用。记得在正式环境中对版本和网络做更细致的规划。