
本文详解如何在docker开发环境中让两个独立的compose项目(管理前端+后端api)通过自定义桥接网络实现可靠、可解析的容器间通信,重点解决enotfound域名解析失败、服务不可达等常见问题。
本文详解如何在docker开发环境中让两个独立的compose项目(管理前端+后端api)通过自定义桥接网络实现可靠、可解析的容器间通信,重点解决enotfound域名解析失败、服务不可达等常见问题。
在微服务或模块化前端开发中,常需将管理控制台(如Next.js + Express)与独立API服务(如Express后端)拆分为两个Docker Compose项目进行并行开发。但若未正确配置网络拓扑,容器将无法通过服务名相互发现——正如你遇到的错误 Error: getaddrinfo ENOTFOUND ocd-api-service-app-1,本质是DNS解析失败:Docker内置DNS仅在同一Compose项目内自动注册服务别名,跨项目容器默认处于隔离网络,彼此不可见。
✅ 正确解法:复用外部网络 + 显式服务命名
核心原则是:让两个Compose项目接入同一个外部桥接网络,并为API服务赋予唯一、可被另一项目识别的服务名。
第一步:统一创建可共享的外部网络
在任意一方(推荐在API服务侧)先创建命名网络(仅需执行一次):
docker network create ocd-network
⚠️ 注意:此网络必须显式创建,不能仅靠networks: { ocd-network: { driver: bridge } }在Compose中声明——后者会创建同名但互不关联的“内部”网络。
第二步:修改双方 compose-dev.yaml,接入外部网络
✅ API服务(api-service/compose-dev.yaml)
重命名服务为 api(避免与mgmt-service中的app冲突),并绑定到外部网络:
networks:
ocd-network:
external: true # 关键:声明为已存在外部网络
services:
api: # ← 唯一且语义清晰的服务名
entrypoint: ["sleep", "infinity"]
image: docker/dev-environments-javascript:stable-1
networks:
- ocd-network # 加入共享网络
init: true
volumes:
- /var/run/docker.sock:/var/run/docker.sock
ports:
- "3001:3001" # 可选:便于本地调试访问
✅ 管理服务(mgmt-service/compose-dev.yaml)
同样接入同一外部网络,并确保服务名不冲突(保留app即可):
networks:
ocd-network:
external: true
services:
app:
entrypoint: ["sleep", "infinity"]
image: docker/dev-environments-javascript:stable-1
networks:
- ocd-network # 关键:与API服务同网
init: true
volumes:
- /var/run/docker.sock:/var/run/docker.sock
第三步:更新代码中的请求地址
在 mgmt-service/app.cjs 中,将硬编码的错误主机名 ocd-api-service-app-1 替换为Compose中定义的服务名 api(Docker DNS会自动解析为对应容器IP):
// ✅ 正确:使用服务名 + 端口(注意:端口是容器内监听端口,非宿主机映射端口)
const response = await axios.get("http://api:3001/test");
? 验证技巧:进入mgmt-service容器手动测试连通性
docker exec -it ocd-mgmt-service-app-1 sh # 在容器内执行: ping api # 应能解析并ping通 curl http://api:3001/test # 应返回预期JSON
第四步:确保API服务实际监听正确端口
你的 api-service/index.ts 中使用了 process.env.PORT,但未提供默认值或验证。务必确认该环境变量已设置为 3001,或显式指定:
const port = parseInt(process.env.PORT || '3001', 10); // 显式fallback
app.listen(port, () => {
console.log(`✅ API service running on port ${port}`);
});
同时,在API服务的Compose中添加环境变量声明(推荐):
services:
api:
# ... 其他配置
environment:
- PORT=3001
? 关键注意事项总结
| 问题现象 | 根本原因 | 解决方案 |
|---|---|---|
| ENOTFOUND ocd-api-service-app-1 | 跨Compose项目无DNS互通 | 使用同一外部网络 + 服务名直连 |
| Connection refused | API容器未监听3001端口或未暴露 | 检查app.listen()端口与环境变量一致性 |
| 请求超时/500错误 | 容器间网络策略拦截(极少见) | 确认Docker守护进程未启用--icc=false(默认开启) |
| 本地浏览器访问/api/proxy失败 | 请求由浏览器发起(非Node.js服务器) | 你当前逻辑正确:/api/proxy是服务端代理,需确保Next.js API路由走Node层 |
✅ 最终验证流程
- 启动API服务:cd api-service && docker compose -f compose-dev.yaml up -d
- 启动管理服务:cd mgmt-service && docker compose -f compose-dev.yaml up -d
- 查看网络连接:docker network inspect ocd-network → 确认两容器均在Containers列表中
- 点击UI按钮触发/api/proxy → 控制台应输出 "Winner, winner chicken dinner"
至此,两个Docker开发环境已构建起稳定、可维护的内部通信链路,为后续集成测试、灰度发布及Swarm/K8s迁移奠定坚实基础。
大量免费API接口:立即使用
涵盖生活服务API、金融科技API、企业工商API、等相关的API接口服务。免费API接口可安全、合规地连接上下游,为数据API应用能力赋能!











