0%
使用 docker-compose 部署一个 egg.js 应用
2023-8-28
计划是使用docker-compose编排三个服务:
- nginx
- node
- mysql
nginx 的配置、node 应用的环境变量、mysql 的配置和数据文件均外挂出来。
下面是 docker-compose.yml
yml
version: '3'
services:
nginx:
image: nginx:latest
env_file:
- ./docker/docker.env
ports:
- "80:80"
volumes:
- ./docker/nginx/nginx.conf:/etc/nginx/conf.d/default.conf
depends_on:
- node
node:
image: node:14
env_file:
- ./docker/docker.env
working_dir: /www
volumes:
- .:/www
command: "./docker/init.sh"
depends_on:
- mysql
ports:
- "7001:7001"
mysql:
image: mysql:latest
env_file:
- ./docker/docker.env
working_dir: /www
ports:
- "30001:3306"
volumes:
- ./docker/mysql/init.sh:/www/init.sh
- ./docker/mysql/init.sql:/www/init.sql
- ./docker/mysql/my.cnf:/etc/my.cnf
- ./docker/mysql/data:/var/lib/mysql
为了让目录结构更像一个应用层项目而不是一个docker配置,我要把项目代码放在根目录,docker 作为一个子目录放在项目目录下。应用目录结构如下。
.
├── app
├── config
├── docker (docker 相关的放在这)
│ ├── mysql
│ │ └── data
│ └── nginx
├── logs
├── public
├── run
└── test
docker 相关又分为mysql、nginx、应用配置和启动脚本。docker 目录下文件和目录结构如下。
.
├── docker.env
├── docker.env.example
├── init.sh
├── mysql
│ ├── data
│ │ └── (mysql 数据文件)
│ ├── init.sql
│ └── my.cnf
└── nginx
└── nginx.conf
docker.env 中配置环境变量,并在 docker-compose.yml 中引用。
APP_ENV: local
APP_DOMAIN=bean-local.xtzero.me
APP_RUN_CMD=dev
MYSQL_ROOT_PASSWORD: 12345678
MYSQL_DATABASE: bean
MYSQL_USER: mysql
MYSQL_PASSWORD: 12345678
init.sh 中配置应用的启动脚本,并在 node 容器中执行。
sh
npm install
echo copy config/env
touch /www/config/env
echo ${APP_ENV} > /www/config/env
npm run ${APP_RUN_CMD}
mysql/init.sql 中存的是 mysql 的启动脚本,可以在第一次启动服务的时候初始化数据库表结构。
nginx/nginx.conf 中存放 nginx 的配置,外挂出来是方便修改。
mysql/data 是 mysql 的数据目录,外挂出来是为了持久化存储。
一切都配置好了之后尝试在本地启动,然后写业务代码。在本地调试好了之后上服务器部署。最坑的事来了。服务器内存满了。突然就体现了个人开发者的窘迫。没办法升级内存,就只能阉割掉 docker-compose 里的 mysql 了。这样就不如让这个项目和其他项目一起用公共的 mysql 了。于是这个项目就变成了,在本地开发用 docker,在生产环境用普通 egg.js 的方式启动。