使用Docker-Compose时Sequelize迁移出现ECONNREFUSED错误
问题原因分析
你碰到的这个问题是Docker Compose里depends_on的典型坑——它只保证容器的启动顺序,但不会等MySQL服务完全初始化就绪。当你的应用容器开始执行sequelize db:migrate时,数据库容器虽然已经启动,但MySQL可能还在加载系统表、初始化权限,压根没准备好接收连接,所以才会抛出ECONNREFUSED错误。
另外还有个小细节:你的database.js里用到了DB_PASSWORD和DB_NAME环境变量,但docker-compose的app服务配置里没传这俩参数,默认值虽然能凑合用,但最好统一配置避免后续出问题。
解决方案1:用等待脚本做前置检查(推荐)
可以在应用启动前先检测MySQL服务是否可用,常用的工具是wait-for-it.sh脚本,步骤如下:
- 下载脚本到项目根目录:
curl -O https://raw.githubusercontent.com/vishnubob/wait-for-it/master/wait-for-it.sh chmod +x wait-for-it.sh - 修改docker-compose.yml的app服务命令,让它先等MySQL就绪再启动:
app: build: . ports: - '3333:3333' command: ["./wait-for-it.sh", "database:3306", "--", "yarn", "start"] environment: - DB_HOST=database - DB_USER=root - DB_PASSWORD=123123 # 补上缺失的环境变量 - DB_NAME=test depends_on: - database
解决方案2:在代码里加连接重试逻辑
自己写个简单的Node.js脚本,循环尝试连接数据库,成功后再执行迁移:
- 新建
wait-for-db.js文件:const { Sequelize } = require('sequelize'); const config = require('./src/config/database'); const sequelize = new Sequelize(config.database, config.username, config.password, { host: config.host, dialect: 'mysql' }); async function checkDBConnection() { try { await sequelize.authenticate(); console.log('数据库连接成功,开始执行迁移...'); process.exit(0); } catch (err) { console.log('数据库还没就绪,2秒后重试...'); setTimeout(checkDBConnection, 2000); } } checkDBConnection(); - 修改package.json的启动脚本:
"scripts": { "wait-for-db": "node wait-for-db.js", "start": "yarn wait-for-db && npx sequelize db:migrate && npx sequelize db:seed:all && node src/app/index.js" },
解决方案3:用Docker Compose健康检查(需Compose 3.4+)
给数据库服务添加健康检查,让应用容器只在数据库真正就绪后启动:
version: '3.8' services: database: image: mysql:5.7 command: --default-authentication-plugin=mysql_native_password restart: always environment: - MYSQL_ROOT_PASSWORD=123123 - MYSQL_DATABASE=test healthcheck: test: ["CMD", "mysqladmin", "ping", "-h", "localhost", "-u", "root", "-p123123"] interval: 5s timeout: 5s retries: 5 app: build: . ports: - '3333:3333' command: yarn start environment: - DB_HOST=database - DB_USER=root - DB_PASSWORD=123123 - DB_NAME=test depends_on: database: condition: service_healthy
内容的提问来源于stack exchange,提问作者Matheus Campos da Silva
相关产品推荐
相关产品推荐

