docker compose 中控制启动顺序
docker compose 能够根据服务的依赖来决定启动顺序,比如可以强制通过depends_on
指定依赖。但是有些服务启动时间较长,比如数据库,仅仅”启动“不代表服务可以用,最终可能会导致依赖它的服务启动失败。
官方提供一个解决思路,就是把相关的启动命令做一层封装,执行其依赖服务是否已经成功可用,再启动相应的服务。
#!/bin/sh
# wait-for-postgres.sh
set -e
host="$1"
shift
cmd="$@"
until PGPASSWORD=$POSTGRES_PASSWORD psql -h "$host" -U "postgres" -c '\q'; do
>&2 echo "Postgres is unavailable - sleeping"
sleep 1
done
>&2 echo "Postgres is up - executing command"
exec $cmd
启动命令用以下命令覆盖:
command: ["./wait-for-postgres.sh", "db", "python", "app.py"]
https://docs.docker.com/compose/startup-order/
通过环境变量配置参数
12-factor 最佳实践推荐通过环境变量实现参数的配置。
然而实践中常常遇到以下问题:
- 如果没有相关配置文件,使用者很难知道要提供哪些环境变量。
- 如果有配置文件,并推送到远程分支,一方面存在泄漏密码的风险,而且实际运行时往往需要改动配置文件,才能正确运行程序。
- 如果每次都使用环境变量来进行测试验证,使用体验上比使用配置文件要麻烦。
下面提供一个我实践的思路。
- 提供配置文件,但配置参数全部使用本地测试数据。例如一个
config.py
文件,内容如下:
db_name = 'my_db'
db_addr = '127.0.0.1'
db_passwd = 'my_passwd'
# 将环境变量替换本地变量
import os
config = globals()
for v_name, v_value in config.items():
if v_name not in os.environ:
continue
v_type = type(v_value)
config[v_name] = v_type(environ[v_name])
# 引入外部变量
if os.path.exists('env.py'):
from env import *
这样可以在不改动config.py
情况下,通过环境变量,或者填充env.py
来实现覆盖原有的config.py
文件。这样通过环境变量和固定的配置文件都可以覆盖原有的配置文件,而不需要改变原有的config.py
文件。
提示:如果使用 git 管理分支,可以通过.gitignore
文件添加env.py
忽略掉这个文件的上传。
网友评论