千家信息网

docker中compose如何控制服务启动顺序

发表于:2026-11-02 作者:千家信息网编辑
千家信息网最后更新 2026年11月02日,这篇文章将为大家详细讲解有关docker中compose如何控制服务启动顺序,小编觉得挺实用的,因此分享给大家做个参考,希望大家阅读完这篇文章后可以有所收获。概要docker-compose 可以方便
千家信息网最后更新 2026年11月02日docker中compose如何控制服务启动顺序

这篇文章将为大家详细讲解有关docker中compose如何控制服务启动顺序,小编觉得挺实用的,因此分享给大家做个参考,希望大家阅读完这篇文章后可以有所收获。

概要

docker-compose 可以方便组合多个 docker 容器服务, 但是, 当容器服务之间存在依赖关系时, docker-compose 并不能保证服务的启动顺序.

docker-compose 中的 depends_on 配置是容器的启动顺序, 并不是容器中服务的启动顺序.

问题重现

首先, 我们构造一个示例, 来演示 docker-compose 带来的问题. docker-compose.yml 文件如下:

version: '2'services: web:  image: ubuntu:14.04  depends_on:   - web  command: nc -z database 3306 database:  image: ubuntu:14.04  command: >   /bin/bash -c '   sleep 5;   echo "sleep over";   nc -lk 0.0.0.0 3306;   '

启动后, 可以发现, 确实是先启动 database, 后启动 web, 但是 database 中的服务是在大约 5 秒后才完成的, 所以导致 web 的启动失败.

$ docker-compose upCreating tmp_database_1 ... doneCreating tmp_database_1 ...Creating tmp_web_1   ... doneAttaching to tmp_database_1, tmp_web_1tmp_web_1 exited with code 1database_1 | sleep over

问题解决方式 1.0

修改 web 的启动脚本, 等待 database 的端口通了之后再启动服务

version: '2'services: web:  image: ubuntu:14.04  depends_on:   - database  command: >   /bin/bash -c '   while ! nc -z database 3306;   do    echo "wait for database";    sleep 1;   done;   echo "database is ready!";   echo "start web service here";   ' database:  image: ubuntu:14.04  command: >   /bin/bash -c '   sleep 5;   echo "sleep over";   nc -lk 0.0.0.0 3306;   '

再次启动,

$ docker-compose upCreating tmp_database_1 ... doneCreating tmp_database_1 ...Creating tmp_web_1   ... doneAttaching to tmp_database_1, tmp_web_1web_1    | wait for databaseweb_1    | wait for databaseweb_1    | wait for databaseweb_1    | wait for databaseweb_1    | wait for databasedatabase_1 | sleep overweb_1    | database is ready!web_1    | start web service heretmp_web_1 exited with code 0

web 会在 database 启动完成, 端口通了之后才启动.

问题解决方式 2.0

上面的解决方式虽然能够解决问题, 但是在 yaml 中直接插入脚本不好维护, 也容易出错. 如果有多个依赖, 或者多层依赖的时候, 复杂度会直线上升.

所以, 要封装一个 entrypoint.sh 脚本, 可以接受启动命令, 以及需要等待的服务和端口. 脚本内容如下:

#!/bin/bash#set -x#******************************************************************************# @file  : entrypoint.sh# @author : wangyubin# @date  : 2018-08- 1 10:18:43## @brief  : entry point for manage service start order# history : init#******************************************************************************: ${SLEEP_SECOND:=2}wait_for() {  echo Waiting for $1 to listen on $2...  while ! nc -z $1 $2; do echo waiting...; sleep $SLEEP_SECOND; done}declare DEPENDSdeclare CMDwhile getopts "d:c:" argdo  case $arg in    d)      DEPENDS=$OPTARG      ;;    c)      CMD=$OPTARG      ;;    ?)      echo "unkonw argument"      exit 1      ;;  esacdonefor var in ${DEPENDS//,/ }do  host=${var%:*}  port=${var#*:}  wait_for $host $portdoneeval $CMD

这个脚本有 2 个参数, -d 需要等待的服务和端口, -c 等待的服务和端口启动之后, 自己的启动命令

修改 docker-compose.yml, 使用 entrypoint.sh 脚本来控制启动顺序.

version: '2'services: web:  image: ubuntu:14.04  depends_on:   - database  volumes:   - "./entrypoint.sh:/entrypoint.sh"  entrypoint: /entrypoint.sh -d database:3306 -c 'echo "start web service here"'; database:  image: ubuntu:14.04  command: >   /bin/bash -c '   sleep 5;   echo "sleep over";   nc -lk 0.0.0.0 3306;   '

实际使用中, 也可以将 entrypoint.sh 打包到发布的镜像之中, 不用通过 volumes 配置来加载 entrypoint.sh 脚本.

测试结果如下:

$ docker-compose upStarting tmp_database_1 ... doneStarting tmp_web_1 ... doneAttaching to tmp_database_1, tmp_web_1web_1    | Waiting for database to listen on 3306...web_1    | waiting...web_1    | waiting...web_1    | waiting...database_1 | sleep overweb_1    | start web service heretmp_web_1 exited with code 0

补充

依赖多个服务和端口

使用上面的 entrypoint.sh 脚本, 也可以依赖多个服务和端口, -d 参数后面的多个服务和端口用逗号(,)隔开.

version: '2'services: web:  image: ubuntu:14.04  depends_on:   - mysql   - postgresql  volumes:   - "./entrypoint.sh:/entrypoint.sh"  entrypoint: /entrypoint.sh -d mysql:3306,postgresql:5432 -c 'echo "start web service here"'; mysql:  image: ubuntu:14.04  command: >   /bin/bash -c '   sleep 4;   echo "sleep over";   nc -lk 0.0.0.0 3306;   ' postgresql:  image: ubuntu:14.04  command: >   /bin/bash -c '   sleep 8;   echo "sleep over";   nc -lk 0.0.0.0 5432;   '

执行的效果可以自行尝试.

尝试间隔的配置

每次尝试连接的等待时间可以通过 环境变量 SLEEP_SECOND 来配置, 默认 2 秒 下面的配置等待时间设置为 4 秒, 就会每隔 4 秒才去尝试 mysql 服务时候可连接.

version: '2'services: web:  image: ubuntu:14.04  environment:   SLEEP_SECOND: 4  depends_on:   - mysql  volumes:   - "./entrypoint.sh:/entrypoint.sh"  entrypoint: /entrypoint.sh -d mysql:3306 'echo "start web service here"'; mysql:  image: ubuntu:14.04  command: >   /bin/bash -c '   sleep 4;   echo "sleep over";   nc -lk 0.0.0.0 3306;   '

关于"docker中compose如何控制服务启动顺序"这篇文章就分享到这里了,希望以上内容可以对大家有一定的帮助,使各位可以学到更多知识,如果觉得文章不错,请把它分享出去让更多的人看到。

服务 端口 脚本 顺序 多个 问题 配置 容器 尝试 控制 方式 篇文章 面的 内容 参数 命令 时候 时间 是在 更多 数据库的安全要保护哪些东西 数据库安全各自的含义是什么 生产安全数据库录入 数据库的安全性及管理 数据库安全策略包含哪些 海淀数据库安全审计系统 建立农村房屋安全信息数据库 易用的数据库客户端支持安全管理 连接数据库失败ssl安全错误 数据库的锁怎样保障安全 新华互联网科技 科技互联网企业 互联网和科技技术 互联网科技公司税收优惠 天津摩尔互联网科技 中国互联网金融科技基金 互联网金融监管科技 青岛中康互联网医疗科技有限公司 广州慧亚互联网科技怎么样 顶级互联网科技成果有哪些 岳阳华臻互联网科技有限公司 厦门千工互联网科技有限公司 燊美集互联网科技有限公司 互联网金融科技名词解释 中国互联网有什么科技 张召忠谈中国互联网科技 广州燕处互联网科技有限公司 西安有哪些互联网高科技企业 广州梦谷互联网科技有限公司领导 银川新华互联网科技学校原画 互联网科技有限公司图片 兼蜜互联网科技 互联网科技网站 互联网科技类展会 中正互联网科技招聘 科技互联网的估值 互联网公司黑科技创始人 为客找房互联网科技公司怎么样 广东鹅鹅鹅互联网科技有限公司 福仕德教育科技互联网
0