Docker Compose启动Go+MariaDB项目时crudapi容器立即退出问题排查
问题原因梳理
- Dockerfile中依赖安装步骤被注释,若项目未提前在本地将依赖写入
go.mod/go.sum或打包到vendor目录,构建阶段无法识别gin、mysql驱动等依赖,会导致程序启动失败直接退出。 - MariaDB配置存在两处错误:一是数据卷挂载路径错误,官方mariadb镜像的数据默认存储路径为
/var/lib/mysql而非/var/lib/mysql/data;二是环境变量配置冲突,MYSQL_USER设为root属于无效配置,root用户的密码仅由MYSQL_ROOT_PASSWORD控制,额外配置MYSQL_USER=root+MYSQL_PASSWORD=root会导致数据库权限初始化异常。 - Go应用数据库连接地址配置错误:容器内的localhost指向crudapi容器自身,默认写的
127.0.0.1:3306无法访问db容器的MariaDB服务,连接失败后程序无阻塞逻辑直接执行完退出,所以返回退出码0。 depends_on仅保证容器启动顺序,不保证MariaDB完成初始化、可以接受TCP连接,Go服务启动时早于数据库就绪,会因连接失败直接退出。
修复方案
1. 修正Dockerfile配置
优先拷贝依赖文件利用Docker层缓存,删除注释的旧版go get逻辑,使用go mod管理依赖:
FROM golang:1.17 WORKDIR /src/app # 优先拷贝依赖文件,提前下载依赖 COPY go.mod go.sum ./ RUN go mod download COPY . . RUN go build -o app . CMD [ "./app" ]
2. 修正docker-compose.yml配置
修复数据库配置,增加健康检查保证数据库就绪后再启动Go服务:
version: '3.8' services: db: container_name: appdb image: mariadb:latest volumes: - ./dbdata:/var/lib/mysql environment: MYSQL_ROOT_PASSWORD: "root" MYSQL_DATABASE: "crudapp" # 数据库健康检查,确认可接受连接后再标记服务就绪 healthcheck: test: ["CMD", "mysqladmin" ,"ping", "-h", "localhost", "-uroot", "-proot"] timeout: 20s retries: 10 app: container_name: crudapi build: context: . ports: - '8080:8080' depends_on: db: condition: service_healthy # 异常退出自动重启 restart: on-failure
3. 修正Go应用数据库连接配置
将代码中数据库连接地址从127.0.0.1:3306改为db:3306,DSN示例如下:
dsn := "root:root@tcp(db:3306)/crudapp?charset=utf8mb4&parseTime=True&loc=Local"
建议在数据库连接逻辑处增加错误日志打印,方便快速定位连接失败的具体原因。
4. 重新启动服务
执行以下命令清理旧资源并重建启动:
docker-compose down -v docker-compose up --build
内容的提问来源于stack exchange,提问作者John Doah
相关产品推荐
相关产品推荐

