通过 .env 文件的命令扩展为 `docker 运行` 生成参数
Generating parameters for `docker run` through command expansion from .env files
我在以相对通用的方式将一些环境参数传递给 docker run
时遇到了一些问题。
我们的第一次迭代是通过这些行将 .env
文件加载到环境中:
set -o allexport;
. "${PROJECT_DIR}/.env";
set +o allexport;
然后手动键入 --env VARNAME=$VARNAME
作为 docker run
命令的选项。但是当你有几十个变量时,这会很烦人。
然后我们尝试用 --env-file .env
传递文件,它 似乎 可以工作,但它没有,因为它不能很好地与引用变量值。
这是我开始做 crazy/ugly 事情的地方。基本想法是做类似的事情:
set_docker_parameters()
{
grep -v '^$' "${PROJECT_DIR}/.env" | while IFS= read -r LINE; do
printf " -e %s" "${LINE}"
done
}
docker run $(set_docker_parameters) --rm image:label command
其中解析的行类似于 VARIABLE="value"
、VARIABLE='value'
或 VARIABLE=value
。空行被管道 grep
.
丢弃
但是docker run
总是抱怨没有被正确调用。当我扩展 set_docker_parameters
的结果时,我得到了预期的结果,当我复制它的结果并替换 $(set_docker_parameters)
时,docker run
也按预期工作,完美无瑕。
知道我做错了什么吗?
非常感谢!
P.S.: 我试图让我的脚本 100% POSIX 兼容,所以我更喜欢任何不依赖 Bash 特定功能的解决方案.
根据@jordanm 的评论,我设计了以下解决方案:
docker_run_wrapper()
{
# That's not ideal, but in any case it's not directly related to the question.
cmd=
set --; # Unset all positional arguments ($@ will be emptied)
# We don't have arrays (we want to be POSIX compatible), so we'll
# use $@ as a sort of substitute, appending new values to it.
grep -v '^$' "${PROJECT_DIR}/.env" | while IFS= read -r LINE; do
set -- "$@" "--env";
set -- "$@" "${LINE}";
done
# We use $@ in a clearly non-standard way, just to expand the values
# coming from the .env file.
docker run "$@" "image:label" /bin/sh -c "${cmd}";
}
话又说回来,这不是我为特定用例编写的代码,而是显示基本思想的简化代码。如果您可以依赖 Bash,那么它可以更简洁,不重载 $@
并使用数组。
我在以相对通用的方式将一些环境参数传递给 docker run
时遇到了一些问题。
我们的第一次迭代是通过这些行将 .env
文件加载到环境中:
set -o allexport;
. "${PROJECT_DIR}/.env";
set +o allexport;
然后手动键入 --env VARNAME=$VARNAME
作为 docker run
命令的选项。但是当你有几十个变量时,这会很烦人。
然后我们尝试用 --env-file .env
传递文件,它 似乎 可以工作,但它没有,因为它不能很好地与引用变量值。
这是我开始做 crazy/ugly 事情的地方。基本想法是做类似的事情:
set_docker_parameters()
{
grep -v '^$' "${PROJECT_DIR}/.env" | while IFS= read -r LINE; do
printf " -e %s" "${LINE}"
done
}
docker run $(set_docker_parameters) --rm image:label command
其中解析的行类似于 VARIABLE="value"
、VARIABLE='value'
或 VARIABLE=value
。空行被管道 grep
.
但是docker run
总是抱怨没有被正确调用。当我扩展 set_docker_parameters
的结果时,我得到了预期的结果,当我复制它的结果并替换 $(set_docker_parameters)
时,docker run
也按预期工作,完美无瑕。
知道我做错了什么吗?
非常感谢!
P.S.: 我试图让我的脚本 100% POSIX 兼容,所以我更喜欢任何不依赖 Bash 特定功能的解决方案.
根据@jordanm 的评论,我设计了以下解决方案:
docker_run_wrapper()
{
# That's not ideal, but in any case it's not directly related to the question.
cmd=
set --; # Unset all positional arguments ($@ will be emptied)
# We don't have arrays (we want to be POSIX compatible), so we'll
# use $@ as a sort of substitute, appending new values to it.
grep -v '^$' "${PROJECT_DIR}/.env" | while IFS= read -r LINE; do
set -- "$@" "--env";
set -- "$@" "${LINE}";
done
# We use $@ in a clearly non-standard way, just to expand the values
# coming from the .env file.
docker run "$@" "image:label" /bin/sh -c "${cmd}";
}
话又说回来,这不是我为特定用例编写的代码,而是显示基本思想的简化代码。如果您可以依赖 Bash,那么它可以更简洁,不重载 $@
并使用数组。