Docker环境下MySQL容器连接被拒绝问题排查及端口/主机配置咨询
解决TypeORM迁移后Docker容器间数据库连接失败问题
核心问题分析
你遇到的connect ECONNREFUSED 127.0.0.1:7201错误,根源在于容器间通信的主机名配置错误:在Docker Compose环境中,每个容器都是独立的网络节点,localhost在users-service容器里指向容器自身,而不是users-service-db容器。另外,你对端口映射的理解也有偏差,导致用错了端口。
Docker Compose端口与网络说明
先明确你疑问的两个配置:
ports: "7201:3306":这是宿主机到容器的端口映射,格式是宿主机端口:容器内部端口。意思是把宿主机的7201端口转发到users-service-db容器的3306端口(MySQL默认端口),这个配置是给宿主机外部或宿主机本身访问数据库用的,容器之间通信不需要用这个映射端口。expose: 7201:这个配置其实是多余且错误的。expose的作用是声明容器对外暴露的端口(仅作文档用,不实际限制访问),但你的MySQL容器内部跑在3306,所以应该expose: 3306才对——不过在Docker Compose的默认网络里,同一compose文件的服务之间可以直接访问彼此的所有容器端口,不需要expose配置也能通信。
另外,你的users-service-db环境变量里的MYSQL_HOST=localhost是冗余的,MySQL容器默认会监听容器内部的所有地址,不需要手动设置这个变量,建议删除,避免干扰。
具体修复步骤
1. 修改数据库连接配置
把connection.ts和typeOrmConfig.ts中的数据库连接配置改成如下:
// connection.ts示例修改 export const initConnection = async () => { connection = await createConnection({ type: "mysql", host: "users-service-db", // 用Docker Compose的服务名作为主机名 port: 3306, // 用容器内部的MySQL端口,不是宿主机映射的7201 username: "root", password: "password", database: "db", // 其他原有配置不变 }); };
// typeOrmConfig.ts示例修改 export = { type: "mysql", host: "users-service-db", port: 3306, username: "root", password: "password", database: "db", // 其他原有配置不变 };
2. 修正Docker Compose配置
更新users-service-db的配置,去掉冗余项:
users-service-db: environment: - MYSQL_PASSWORD=password - MYSQL_DATABASE=db - MYSQL_USER=root - MYSQL_ROOT_PASSWORD=password # 删除MYSQL_HOST=localhost,不需要这个配置 restart: always image: mysql:5.7.20 # 可以保留expose: 3306作为文档,或者直接删掉 expose: - 3306 ports: - "7201:3306" # 这个保留,方便宿主机访问数据库
3. 处理未处理Promise拒绝警告
在initConnection函数中添加错误捕获,避免Node.js的警告:
export const initConnection = async () => { try { connection = await createConnection({ // 修改后的配置 }); console.log("成功连接到数据库"); } catch (error) { console.error("数据库连接失败:", error); // 可以选择抛出错误让上层处理,或者直接退出进程 process.exit(1); } };
验证修复
修改完成后,重启所有容器:
docker-compose down && docker-compose up --build
这样users-service就能正常连接到users-service-db容器了,迁移后的数据库连接问题也会解决。
内容的提问来源于stack exchange,提问作者edibIsic
相关产品推荐
相关产品推荐

