前阵子帮客户迁移服务器,WordPress、MySQL、Redis、Nginx 一个个装,装一下午,装完还各种版本冲突——PHP 版本不对、MySQL 字符集有问题、Nginx 配置文件改来改去……最后客户说了句让我汗颜的话:"李工,有没有更快的办法?我上次看别人装东西,几行命令就搞定了。"
我当场被问住了。是啊,都 2026 年了,我还在手动一个个编译装软件,这效率确实太低了。回来之后我花了一周把 Docker 重新系统学了一遍,把手上 90% 的服务都迁到了 Docker 里,现在部署一个 WordPress 从"半小时"变成"2 分钟",迁移服务器从"一下午"变成"5 分钟"。
今天把这套东西完整写出来。不管你是 Docker 零基础新手,还是用过一两次但总觉得云里雾里,看完这篇你都能独立用 Docker 部署常见服务。全程命令都是亲测可用的,复制粘贴就能跑。
一、先搞懂:Docker 到底是什么?
很多人第一次接触 Docker 会被各种名词绕晕:容器、镜像、Compose、Kubernetes……别急,先说最核心的。
用一句话说清楚 Docker
Docker 就是给软件打包的工具。你可以把一个软件和它需要的所有依赖(库、配置文件、环境变量)打包成一个"集装箱"(叫镜像),这个集装箱搬到任何装了 Docker 的机器上都能直接跑,不会出现"在我电脑上好好的怎么到你这就不行了"的问题。

图 1:Docker 容器 vs 传统虚拟机架构对比
最直观的对比:
| 对比项 | 虚拟机(VM) | Docker 容器 |
|---|---|---|
| 启动速度 | 几分钟 | 几秒 |
| 硬盘占用 | 几 GB 一个 | 几十 MB 一个 |
| 性能损耗 | 10–20% | 几乎零损耗 |
| 隔离级别 | 完全独立操作系统 | 共享内核,进程级隔离 |
| 迁移难度 | 麻烦,要导出导入 | 一个文件拷过去直接跑 |
几个必须知道的名词
- 镜像(Image):软件的"安装包",比如
nginx:latest、mysql:8.0,只读的 - 容器(Container):镜像跑起来的实例,一个镜像可以跑多个容器
- Dockerfile:构建镜像的"配方文件",写清楚怎么打包
- docker-compose.yml:多容器编排文件,把多个服务的配置写在一个文件里,一条命令全启动
- 数据卷(Volume):容器的数据持久化目录,容器删了数据还在
- 端口映射:把容器内的端口映射到宿主机上,外部才能访问
? 新手怎么理解? 镜像 = 菜谱,容器 = 照着菜谱做出来的菜,Compose = 一桌宴席的完整菜单,数据卷 = 装菜的盘子(菜倒了盘子还在)。
二、安装 Docker:3 步搞定(Ubuntu/Debian/CentOS 通用)
别去官网看什么复杂的安装文档,用官方一键脚本最快。
第一步:安装 Docker
# Ubuntu/Debian 一键安装
curl -fsSL https://get.docker.com | sh
# 安装完启动 Docker 并设置开机自启
systemctl enable docker && systemctl start docker
安装完验证一下:
docker --version
# 输出类似:Docker version 24.0.7, build afdd53b
# 跑个 hello-world 测试
docker run hello-world

图 2:Docker 安装成功,运行 hello-world 测试
看到 "Hello from Docker!" 就说明装好了。
第二步:安装 Docker Compose(新版 Docker 已内置)
新版 Docker(20.10+)已经自带了 docker compose 命令(注意中间没有横杠),不用单独装。如果是老版本:
apt install docker-compose-plugin -y
验证:
docker compose version
# Docker Compose version v2.21.0
第三步:配置国内镜像加速(重要!拉镜像会快很多)
国内拉 Docker Hub 镜像经常超时,配置国内加速器:
mkdir -p /etc/docker
cat > /etc/docker/daemon.json << 'EOF'
{
"registry-mirrors": [
"https://docker.mirrors.ustc.edu.cn",
"https://hub-mirror.c.163.com",
"https://mirror.baidubce.com"
]
}
EOF
systemctl daemon-reload && systemctl restart docker
如果你用的是 LuckVM 香港或新加坡节点,直连 Docker Hub 速度很快,不配置也行。国内服务器一定要配。
三、Docker 必学核心命令(15 个够用了)
不用记一大堆命令,日常用的就这些:
镜像相关
docker pull nginx # 拉取镜像
docker images # 查看本地镜像
docker rmi nginx # 删除镜像
docker rmi $(docker images -q) # 删除所有镜像(慎用)
容器相关
docker run -d --name mynginx -p 80:80 nginx # 后台启动容器(-d后台运行,-p端口映射)
docker ps # 查看运行中的容器
docker ps -a # 查看所有容器(包括停止的)
docker stop mynginx # 停止容器
docker start mynginx # 启动容器
docker restart mynginx # 重启容器
docker rm mynginx # 删除容器(要先停止)
docker logs mynginx # 查看容器日志
docker logs -f mynginx # 实时跟踪日志
docker exec -it mynginx bash # 进入容器内部(类似 SSH 登录)
数据卷和清理
docker volume ls # 查看数据卷
docker system prune -a # 清理没用的镜像/容器/缓存(释放磁盘空间)
四、装个图形化面板 Portainer(新手强烈推荐)
命令行记不住?装个 Portainer,浏览器里点点鼠标就能管理所有容器,不用记命令。
docker run -d \
--name portainer \
--restart=always \
-p 9000:9000 \
-v /var/run/docker.sock:/var/run/docker.sock \
-v portainer_data:/data \
portainer/portainer-ce:latest
安装完浏览器访问 http://你的服务器IP:9000,第一次访问设置管理员密码,选择 "Local" 环境,就能看到管理面板了。

图 3:Portainer 可视化管理面板——容器状态一目了然
之后启动/停止/重启容器、查看日志、拉取镜像、看资源占用,全部在网页里点就行。新手先用这个过渡,熟练了再用命令行效率更高。
五、实战:10 个常用服务一键部署
下面 10 个服务,全部用 docker-compose 部署。先创建一个目录放配置文件:
mkdir -p /opt/docker && cd /opt/docker
每个服务都是独立目录,配置文件放进去,一条命令启动。
1. WordPress(建站最常用)
这是最经典的组合:WordPress + MySQL,一条命令搞定。
mkdir -p /opt/docker/wordpress && cd /opt/docker/wordpress
cat > docker-compose.yml << 'EOF'
version: '3'
services:
db:
image: mysql:8.0
restart: always
environment:
MYSQL_ROOT_PASSWORD: your_root_password_改这里
MYSQL_DATABASE: wordpress
MYSQL_USER: wordpress
MYSQL_PASSWORD: your_db_password_改这里
volumes:
- ./db:/var/lib/mysql
wordpress:
depends_on:
- db
image: wordpress:latest
restart: always
ports:
- "8080:80"
environment:
WORDPRESS_DB_HOST: db
WORDPRESS_DB_USER: wordpress
WORDPRESS_DB_PASSWORD: your_db_password_改这里
WORDPRESS_DB_NAME: wordpress
volumes:
- ./html:/var/www/html
EOF
docker compose up -d
启动后访问 http://IP:8080 就能看到 WordPress 安装页面了。

图 4:WordPress + MySQL 容器部署架构,数据通过数据卷持久化
⚠️ 记得改密码:上面
your_root_password_改这里和your_db_password_改这里改成你自己的强密码。? 建议:正式建站不要直接暴露 8080 端口给外网,后面用 Nginx Proxy Manager 配反向代理+SSL,对外只开 80/443。
2. Nginx Proxy Manager(反向代理 + 自动 HTTPS)
这是我必装的第一个服务。有了它,你不需要手动写 Nginx 配置文件,也不用手动申请 SSL 证书,全在网页里点几下就能搞定多个域名的反向代理,自动续期 Let's Encrypt 证书。
mkdir -p /opt/docker/npm && cd /opt/docker/npm
cat > docker-compose.yml << 'EOF'
version: '3'
services:
npm:
image: jc21/nginx-proxy-manager:latest
restart: always
ports:
- "80:80"
- "443:443"
- "81:81"
volumes:
- ./data:/data
- ./letsencrypt:/etc/letsencrypt
EOF
docker compose up -d
访问 http://IP:81,默认账号密码:
- 邮箱:
admin@example.com - 密码:
changeme
第一次登录会让你改密码。进去之后点 "Proxy Hosts" → "Add Proxy Host",填域名、转发到的容器 IP 和端口,勾选 "Request SSL Certificate",点保存就自动配好 HTTPS 了。

图 5:NPM 管理多个域名的反向代理,自动续期 SSL 证书
3. Nextcloud(自建个人/团队网盘)
不想用百度网盘限速?自建一个 Nextcloud,文件、照片、日历、联系人全都存自己服务器上,配合手机 App 自动同步照片。
mkdir -p /opt/docker/nextcloud && cd /opt/docker/nextcloud
cat > docker-compose.yml << 'EOF'
version: '3'
services:
db:
image: mariadb:10.6
restart: always
environment:
MYSQL_ROOT_PASSWORD: nextcloud_root_pw
MYSQL_DATABASE: nextcloud
MYSQL_USER: nextcloud
MYSQL_PASSWORD: nextcloud_db_pw
volumes:
- ./db:/var/lib/mysql
app:
image: nextcloud:latest
restart: always
ports:
- "8081:80"
depends_on:
- db
volumes:
- ./nextcloud:/var/www/html
environment:
MYSQL_HOST: db
MYSQL_DATABASE: nextcloud
MYSQL_USER: nextcloud
MYSQL_PASSWORD: nextcloud_db_pw
EOF
docker compose up -d

图 6:Nextcloud 自建网盘界面——文件管理、照片同步、在线协作
⚠️ 注意:Nextcloud 比较吃内存,建议 2核4G 以上配置,再低会比较卡。
4. RustDesk Server(自建远程桌面)
这个我之前专门写过完整教程。简单给个 Docker Compose 配置,详细部署和配置看这篇教程。
mkdir -p /opt/docker/rustdesk && cd /opt/docker/rustdesk
cat > docker-compose.yml << 'EOF'
version: '3'
services:
hbbs:
image: rustdesk/rustdesk-server:latest
container_name: rustdesk-hbbs
command: hbbs
restart: always
network_mode: host
volumes:
- ./data:/root
hbbr:
image: rustdesk/rustdesk-server:latest
container_name: rustdesk-hbbr
command: hbbr
restart: always
network_mode: host
volumes:
- ./data:/root
EOF
docker compose up -d
# 查看公钥(客户端要填这个)
cat ./data/id_ed25519.pub
启动后客户端填你服务器 IP 和 Key 就能用了,比 TeamViewer 稳定、没有商业检测。
5. Redis(高性能缓存)
跑网站、数据库必备的缓存服务:
mkdir -p /opt/docker/redis && cd /opt/docker/redis
cat > docker-compose.yml << 'EOF'
version: '3'
services:
redis:
image: redis:7-alpine
restart: always
ports:
- "6379:6379"
command: redis-server --requirepass your_redis_password_改这里 --appendonly yes
volumes:
- ./data:/data
EOF
docker compose up -d
生产环境记得改密码,并且不要把 6379 端口暴露到公网(可以只让其他容器访问,不做端口映射,用容器名互联)。
6. MySQL / PostgreSQL 数据库
# MySQL 8.0
mkdir -p /opt/docker/mysql && cd /opt/docker/mysql
cat > docker-compose.yml << 'EOF'
version: '3'
services:
mysql:
image: mysql:8.0
restart: always
ports:
- "3306:3306"
environment:
MYSQL_ROOT_PASSWORD: your_mysql_root_pw
volumes:
- ./data:/var/lib/mysql
command: --character-set-server=utf8mb4 --collation-server=utf8mb4_unicode_ci
EOF
docker compose up -d
7. AdGuard Home(去广告 DNS,全设备免装插件)
这个是真的神器。在 VPS 上跑一个 AdGuard Home,把路由器 DNS 设成你 VPS 的 IP,家里所有设备(手机、电脑、电视、平板)自动去广告、防追踪,不用每个设备装插件。
mkdir -p /opt/docker/adguard && cd /opt/docker/adguard
cat > docker-compose.yml << 'EOF'
version: '3'
services:
adguard:
image: adguard/adguardhome:latest
restart: always
ports:
- "53:53/tcp"
- "53:53/udp"
- "3000:3000"
- "82:80"
volumes:
- ./work:/opt/adguardhome/work
- ./conf:/opt/adguardhome/conf
EOF
docker compose up -d
启动后访问 http://IP:3000 初始化管理后台,之后从 http://IP:82 登录,能看到所有设备的 DNS 查询记录、拦截了多少广告。常用的过滤规则订阅 "AdGuard DNS filter" 和 "EasyList China" 就行,日常上网 90% 的广告和追踪都能拦掉。
8. Uptime Kuma(网站宕机监控)
监控你的网站/服务挂没挂,挂了立刻通过邮件、Telegram、微信、钉钉通知你。我自己所有网站都用它监控。
mkdir -p /opt/docker/uptime-kuma && cd /opt/docker/uptime-kuma
cat > docker-compose.yml << 'EOF'
version: '3'
services:
kuma:
image: louislam/uptime-kuma:1
restart: always
ports:
- "3001:3001"
volumes:
- ./data:/app/data
EOF
docker compose up -d
访问 http://IP:3001,添加要监控的网址,设置通知方式就行。支持 HTTP/HTTPS/TCP/Ping/DNS 等多种监控方式,还能出漂亮的可用性报告(比如"过去 30 天可用性 99.98%")。
9. Grafana + Prometheus(服务器性能监控)
想看服务器 CPU、内存、磁盘、网络的实时和历史数据?装这套组合,比云服务商自带的监控还好用。
mkdir -p /opt/docker/monitoring && cd /opt/docker/monitoring
cat > docker-compose.yml << 'EOF'
version: '3'
services:
prometheus:
image: prom/prometheus:latest
restart: always
ports:
- "9090:9090"
volumes:
- ./prometheus.yml:/etc/prometheus/prometheus.yml
- ./prometheus-data:/prometheus
node-exporter:
image: prom/node-exporter:latest
restart: always
ports:
- "9100:9100"
volumes:
- /proc:/host/proc:ro
- /sys:/host/sys:ro
- /:/rootfs:ro
grafana:
image: grafana/grafana:latest
restart: always
ports:
- "3002:3000"
volumes:
- ./grafana:/var/lib/grafana
environment:
GF_SECURITY_ADMIN_PASSWORD: admin
EOF
# 先写个最简 prometheus 配置
cat > prometheus.yml << 'EOF'
global:
scrape_interval: 15s
scrape_configs:
- job_name: 'node'
static_configs:
- targets: ['node-exporter:9100']
EOF
docker compose up -d
访问 http://IP:3002(默认账号 admin / admin),添加 Prometheus 数据源(地址填 http://prometheus:9090),然后导入 Dashboard ID 1860(Node Exporter Full,Grafana 官方模板市场最火的一个),一张漂亮的监控面板就出来了。

图 7:Grafana 实时监控面板——CPU、内存、磁盘、网络一目了然
10. Vaultwarden(自建密码管理器)
不想用 1Password、Bitwarden 官方版?Vaultwarden 是 Bitwarden 的轻量 Rust 实现,资源占用极低(几十 MB 内存),功能完整,浏览器插件、手机 App 全支持。
mkdir -p /opt/docker/vaultwarden && cd /opt/docker/vaultwarden
cat > docker-compose.yml << 'EOF'
version: '3'
services:
vaultwarden:
image: vaultwarden/server:latest
restart: always
ports:
- "8082:80"
environment:
WEBSOCKET_ENABLED: "true"
SIGNUPS_ALLOWED: "true"
volumes:
- ./data:/data
EOF
docker compose up -d
装完用 NPM 反代到一个域名(比如 vault.yourdomain.com),配好 HTTPS,浏览器装 Bitwarden 插件,服务器地址填你自己的域名,就有一个完全自己掌控的密码管理器了。比 1Password 便宜(免费)、比 LastPass 安全(数据在自己手里)。
⚠️ 自己用的话装完记得把
SIGNUPS_ALLOWED改成"false",防止别人注册。
六、Docker 最佳实践(避坑必读)
1. 数据一定要持久化
这是新手最容易踩的坑:容器删了数据就没了!
凡是有数据的服务(数据库、WordPress、Nextcloud、密码管理器……),一定要配置 volumes 把数据映射到宿主机目录上。比如:
volumes:
- ./data:/var/lib/mysql # 把容器内的 /var/lib/mysql 映射到宿主机的 ./data 目录
这样就算你 docker rm -f 把容器删了,数据还在 ./data 里,下次启动新容器挂上去就行。
2. 一定要加 restart: always
所有服务都加这个参数,服务器重启后 Docker 会自动把容器拉起来,不用你手动一个个启动。不然服务器一重启,所有服务全挂。
3. 不要用 latest 标签(生产环境)
latest 标签每次拉的都是最新版,可能突然大版本更新导致不兼容。生产环境建议固定版本号,比如 mysql:8.0、wordpress:6.4-php8.1-apache,更稳。
4. 定期清理日志和无用镜像
Docker 容器的日志默认会一直累积,跑久了能把磁盘占满:
# 限制容器日志大小(全局配置)
cat > /etc/docker/daemon.json << 'EOF'
{
"log-driver": "json-file",
"log-opts": {
"max-size": "10m",
"max-file": "3"
}
}
EOF
systemctl restart docker
# 清理没用的镜像/容器/缓存(释放磁盘)
docker system prune -a
5. 不要在容器里存东西
记住:容器是一次性的,代码、数据、配置都应该通过 volume 挂载进去,而不是在容器内部修改。随时可以删了容器重建,这才是 Docker 的正确用法。
6. 一个容器跑一个进程
不要在一个容器里既跑 Nginx 又跑 MySQL 又跑 PHP——那跟不用 Docker 没区别。每个容器跑一个服务,用 docker-compose 把它们编排起来,这是最佳实践。
7. 安全注意事项
- 不要把 Docker 守护进程的 2375 端口暴露到公网(会被人当肉鸡)
- 不要用 root 权限运行不必要的容器(能用普通用户就用普通用户)
- 数据库端口(3306/5432/6379)不要直接暴露到公网,通过容器网络内部访问就行
- 镜像尽量从官方仓库拉,别随便用不知名的第三方镜像(可能有后门)

图 8:6 个常见场景下 Docker 部署 vs 传统部署的耗时对比
七、常见问题 FAQ
Q1:拉镜像慢、超时怎么办?
国内服务器配置镜像加速器(前面讲过了);海外节点(LuckVM 香港/新加坡/美国)直连一般没问题;实在不行手动搜"Docker 镜像代理",有很多公益代理。
Q2:端口被占用怎么办?
docker ps 看是哪个容器占用了端口,停掉那个容器或者换个宿主机端口。常见冲突:80/443 被 Nginx/Apache 占用,3306 被主机 MySQL 占用。
Q3:容器启动了但访问不了?
排查顺序:①容器是不是真的在跑(docker ps);②端口映射对不对;③防火墙/安全组有没有开对应端口;④容器内服务是不是真的在监听(docker logs 容器名 看日志)。
Q4:怎么备份数据?
直接把 volume 映射的宿主机目录打包就行。比如:
tar -zcvf backup.tar.gz /opt/docker/wordpress/
恢复的时候解压回去,重新 docker compose up -d 就完全恢复了。
Q5:容器时间不对?
在 docker-compose.yml 里加环境变量:
environment:
- TZ=Asia/Shanghai
或者启动时加 -v /etc/localtime:/etc/localtime:ro。
Q6:2核2G 服务器能跑几个 Docker 服务?
不加监控的话:WordPress + MySQL + NPM + Redis + Uptime Kuma,5个服务完全没问题,内存占用大概 1.2–1.5G。再加 Grafana/Nextcloud 就建议 2核4G 起步。
Q7:Docker 比直接装占资源吗?
几乎不占额外资源。Docker 的性能损耗在 1–2% 以内,你完全感觉不到。真正占资源的是你跑的服务本身,不是 Docker。
Q8:怎么看容器日志?
docker logs 容器名 # 查看全部日志
docker logs -f 容器名 # 实时跟踪
docker logs --tail 100 容器名 # 看最后100行
docker logs -t 容器名 # 带时间戳
Q9:docker-compose 和 docker compose(带横杠/不带横杠)有什么区别?
不带横杠的 docker compose 是新版(V2),作为 Docker 插件存在,推荐用这个。带横杠的 docker-compose 是老版(V1,Python写的),已经停止维护了。
Q10:我现在服务器上都是手动装的,怎么迁移到 Docker?
别一次性全迁,逐步来。新部署的服务用 Docker,老服务等下次维护的时候慢慢迁。迁移步骤:①在新目录写好 docker-compose.yml;②导出老服务数据;③把数据放到 volume 目录;④启动新容器测试;⑤没问题了停掉老服务切流量。
八、Docker 常用命令速查表
# === 基础操作 ===
docker ps # 查看运行中的容器
docker ps -a # 查看所有容器
docker images # 查看本地镜像
docker pull 镜像名 # 拉取镜像
docker start/stop/restart 容器名 # 启动/停止/重启
docker rm 容器名 # 删除容器(先停止)
docker rmi 镜像名 # 删除镜像
docker logs -f 容器名 # 实时查看日志
docker exec -it 容器名 bash # 进入容器
# === Compose 操作(在有 docker-compose.yml 的目录下执行)===
docker compose up -d # 后台启动所有服务
docker compose down # 停止并删除所有容器
docker compose restart # 重启所有服务
docker compose logs -f # 查看所有服务日志
docker compose pull # 拉取最新镜像
docker compose up -d --build # 重新构建并启动
# === 清理维护 ===
docker system prune -a # 清理所有没用的镜像/容器/缓存
docker volume prune # 清理没用的数据卷
docker system df # 查看 Docker 占用磁盘空间
# === 系统相关 ===
systemctl start docker # 启动 Docker
systemctl enable docker # 设置开机自启
systemctl status docker # 查看 Docker 状态
最后
Docker 刚开始学的时候确实觉得概念多、命令杂,但一旦你跑通两三个服务,就会发现这东西是真的香——配置一次,到处运行,再也不用在新服务器上重复"装环境→配配置→调错误"这套流程了。
我现在部署任何新服务,第一件事就是搜"服务名 + docker",90% 的情况官方都有现成的 Docker 镜像,直接抄 docker-compose.yml 就行,几分钟搞定。
新手建议:别一上来就想理解所有概念,先照着本文把 Portainer + Nginx Proxy Manager + WordPress 跑起来,用起来再说,用的过程中遇到问题再查,比看十篇理论文章学得都快。
相关阅读:





