为什么说Docker是开发者离不开的瑞士军刀?
如果你经常和服务器打交道,或者正在为环境配置、依赖冲突、项目迁移这些事头疼,那你一定听说过Docker。但很多人对它的理解停留在“一个虚拟化工具”的层面,这其实低估了它的价值。在笔者看来,Docker更像是一个标准化的软件交付流水线,它把应用及其依赖打包成一个轻量、可移植的容器,让你在任何地方都能以完全一致的方式运行它。
更让人兴奋的是,围绕Docker构建的开源生态极其繁荣。从数据库、缓存、消息队列,到监控、日志、CI/CD工具,几乎所有你需要的中间件和应用,都能找到现成的、由社区维护的高质量镜像。这意味着,我们不再需要从零开始编译安装,只需要几条命令,就能把复杂的服务跑起来。
先搞清楚:Docker镜像与容器的关系
在实操之前,我们得先弄懂两个最核心的概念,否则后面容易绕晕。
- 镜像(Image):它是一个只读的模板,包含了运行应用所需的一切——代码、运行时、系统工具、库文件、配置。你可以把它理解为一个“类”或者“安装光盘”。
- 容器(Container):它是镜像的运行实例,是“类”实例化出来的“对象”。容器可以被启动、停止、删除,且彼此隔离。
简单来说,镜像定义了我们想要什么,容器则是我们正在运行的东西。我们的任务,就是找到合适的镜像,然后把它跑起来。
实战部署:用Docker快速搭建一套实用的开源开发环境
理论说再多,不如动手做一次。接下来,我们以一台全新的Linux服务器(以Ubuntu 22.04为例)作为操作环境,带大家一步步部署几个非常实用的开源软件组合。这套组合可以用于个人博客、小型项目演示,甚至是生产环境的雏形。
第一步:安装Docker引擎(CE版本)
虽然很多云服务商提供了镜像市场一键安装,但掌握手动安装依然是基本功。我们使用官方脚本安装,简单且不易出错。
# 更新apt包索引
sudo apt-get update
# 安装依赖包,允许apt通过HTTPS使用仓库
sudo apt-get install -y ca-certificates curl gnupg lsb-release
# 添加Docker官方GPG密钥
sudo mkdir -p /etc/apt/keyrings
curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo gpg --dearmor -o /etc/apt/keyrings/docker.gpg
# 设置稳定版仓库
echo \
"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/null
# 再次更新索引并安装Docker引擎
sudo apt-get update
sudo apt-get install -y docker-ce docker-ce-cli containerd.io docker-compose-plugin
安装完成后,启动服务并设置开机自启,然后验证一下版本。
sudo systemctl enable docker --now
sudo docker version
看到Client和Server版本信息都输出后,说明Docker引擎已经正常工作了。为了避免每次敲sudo,可以把当前用户加入docker组。
sudo usermod -aG docker $USER
# 退出重新登录终端后生效
第二步:部署Nginx Proxy Manager——可视化反向代理利器
有了Docker,我们第一个要装的不是数据库,而是一个反向代理工具。为什么?因为后续我们可能会部署多个Web应用,比如博客、API服务,它们都占用80和443端口。Nginx Proxy Manager(以下简称NPM)提供了一个漂亮的Web界面,让我们能轻松配置域名转发、SSL证书,而不用去手写复杂的Nginx配置。
首先,创建一个目录存放NPM的数据。
mkdir -p ~/docker/npm && cd ~/docker/npm
创建一个docker-compose.yml文件,这是Docker Compose的核心,它定义了我们要运行的服务。
vim docker-compose.yml
写入以下内容:
version: "3.8"
services:
app:
image: jc21/nginx-proxy-manager:latest
restart: unless-stopped
ports:
- "80:80" # HTTP端口
- "443:443" # HTTPS端口
- "81:81" # NPM管理面板端口
environment:
DB_MYSQL_HOST: "db"
DB_MYSQL_PORT: 3306
DB_MYSQL_USER: "npm"
DB_MYSQL_PASSWORD: "npm_pass"
DB_MYSQL_NAME: "npm"
volumes:
- ./data:/data
- ./letsencrypt:/etc/letsencrypt
depends_on:
- db
db:
image: mariadb:10.8
restart: unless-stopped
environment:
MYSQL_ROOT_PASSWORD: "root_pass"
MYSQL_DATABASE: "npm"
MYSQL_USER: "npm"
MYSQL_PASSWORD: "npm_pass"
volumes:
- ./mysql:/var/lib/mysql
保存退出后,在~/docker/npm目录下执行启动命令:
docker compose up -d
等待镜像拉取并启动。完成后,浏览器访问 http://服务器IP:81,默认登录账号为 admin@example.com,密码为 changeme。首次登录后会强制要求修改密码。到这里,我们的反向代理服务就绪了。
第三步:部署Gitea——轻量级Git代码托管平台
作为一个开发者,代码托管是刚需。虽然GitHub很香,但有时我们希望私有化部署,尤其是企业内部项目。Gitea是一个用Go编写的开源Git服务,资源占用极小,界面清爽,功能却一点不少。
同样,我们为Gitea创建独立目录和配置文件。
mkdir -p ~/docker/gitea && cd ~/docker/gitea
vim docker-compose.yml
version: "3.8"
services:
gitea:
image: gitea/gitea:latest
container_name: gitea
environment:
- USER_UID=1000
- USER_GID=1000
- GITEA__database__DB_TYPE=mysql
- GITEA__database__HOST=db:3306
- GITEA__database__NAME=gitea
- GITEA__database__USER=gitea
- GITEA__database__PASSWD=gitea_pass
restart: unless-stopped
volumes:
- ./data:/data
- /etc/timezone:/etc/timezone:ro
- /etc/localtime:/etc/localtime:ro
ports:
- "3000:3000"
- "2222:22"
depends_on:
- db
db:
image: mysql:8.0
restart: unless-stopped
environment:
- MYSQL_ROOT_PASSWORD=gitea_root
- MYSQL_DATABASE=gitea
- MYSQL_USER=gitea
- MYSQL_PASSWORD=gitea_pass
volumes:
- ./mysql:/var/lib/mysql
启动它:
docker compose up -d
启动后,访问 http://服务器IP:3000 进入Gitea的安装页面。数据库类型选择MySQL,主机地址填 db:3306,数据库名、用户名、密码就填上面Compose文件里对应的值。站点URL可以先填IP,后续绑定域名后可以在管理后台修改。
第四步:绑定域名与HTTPS(通过NPM实现)
现在,Gitea运行在3000端口,我们通过IP加端口访问。这不够专业,也容易暴露服务器端口。我们回到Nginx Proxy Manager的81端口管理面板。
在NPM面板中,点击“Proxy Hosts” -> “Add Proxy Host”。
- Domain Names:填写你的域名,例如
git.yourdomain.com。前提是你已经将该域名的A记录解析到服务器IP。 - Forward Hostname / IP:这里要注意,因为我们是用Compose部署的,NPM和Gitea在同一个Docker网络中,所以可以直接填写服务名称
gitea,或者填写服务器的内网IP。这里我们填gitea。 - Forward Port:填
3000。 - Block Common Exploits:勾选上,增强安全性。
保存后,再进入“SSL”标签页,申请Let’s Encrypt证书。勾选“Force SSL”和“HTTP/2 Support”,填入你的邮箱地址,点击保存。稍等片刻,证书就会自动签发并续期。
现在,你就可以通过 https://git.yourdomain.com 安全地访问你的私人Git服务了。
第五步:部署Uptime Kuma——监控你的服务状态
服务部署好了,但如果宕机了怎么办?我们不可能24小时盯着。Uptime Kuma是一个开源的监控工具,界面美观,支持TCP、HTTP、Ping等多种检测方式,还能通过Telegram、邮件、Webhook等多种渠道发送告警通知。
部署它非常简单,一条命令即可:
docker run -d --restart=always -p 3001:3001 -v ~/docker/uptime-kuma:/app/data --name uptime-kuma louislam/uptime-kuma:latest
启动后,访问 http://IP:3001 创建管理员账号。接着,添加监控项,把之前部署的NPM面板(81端口)、Gitea(3000端口)以及未来的其他服务都加进去。这样,一旦服务出现故障,你就能第一时间收到通知。
进阶技巧:数据卷与容器备份
很多朋友玩Docker最担心的就是数据丢失。其实只要理解了数据卷(Volume)的概念,这个问题就迎刃而解。我们在上面的Compose文件中,已经把./data、./mysql等目录挂载到了宿主机上。这意味着,即使容器被删除,我们的数据依然安全地保存在服务器的磁盘上。
备份时,只需要打包这些宿主机目录即可。例如:
tar -czvf backup_npm.tar.gz ~/docker/npm/data ~/docker/npm/mysql
恢复时,把压缩包解压回原目录,然后重新docker compose up -d即可。这就是容器的可移植性带来的巨大便利。
写在最后:关于成本与选型的一些思考
看到这里,你已经掌握了用Docker快速搭建一套开发/生产环境的核心技能。无论是NPM、Gitea还是Uptime Kuma,它们都是经过千万用户验证的优质开源项目。
不过在最后,笔者想多说一句。玩转Docker离不开一台稳定的服务器。如果你是用个人电脑或低配的云主机跑这些服务,内存和带宽很快就会捉襟见肘。尤其是当我们部署了MySQL、MariaDB这类数据库后,对磁盘I/O和内存的要求会直线上升。如果你希望这些服务能稳定运行,且后续有扩展的需求,那么在采购服务器时,建议选择靠谱的云服务商,并重点关注内存大小(至少4GB起步)和NVMe固态硬盘。同时,正规注册的域名也是必不可少的,它不仅是专业性的体现,更是申请HTTPS证书的前提。
工具是死的,思路是活的。Docker的生态远不止今天我们提到的这几个项目,像Portainer(容器管理)、Nacos(配置中心)、MinIO(对象存储)等,都值得大家去探索。希望这篇文章能成为你探索Docker世界的一块垫脚石,让你在技术的路上走得更轻松一些。
📚 延伸阅读推荐
🎁 全套实操配置文件与 AI 提效资料包免费下载
本文涉及的全套 Docker Compose 配置文件、服务器运维避坑手册及 AI 提效指令库已完整打包上传至夸克网盘,可直接免费极速转存:
💡 提示:推荐使用手机【夸克网盘 App】打开保存,新用户首月免费赠送 1TB 超大空间与免流量极速下载特权。