在NGINX docker容器中启动前运行bash脚本
Running a bash script before startup in an NGINX docker container
我正在尝试使用docker在localhost:8000上运行javascript应用程序。我想做的一部分是根据docker运行命令交换出一些配置文件,我想将一个环境变量传递到容器中,以便bash脚本可以将其用作参数。
我的dockerfile是这样的:
FROM nginx
COPY . /usr/share/nginx/html
CMD ["bash","/usr/share/nginx/html/runfile.sh"]
bash脚本是这样的:
#!/bin/bash
if [ "$SECURITY_VERSION" = "OPENAM" ]; then
sed -i -e 's/localhost/openam/g' authConfig.js
fi
docker run -p 8000:80 missioncontrol:latest -e SECURITY_VERSION="TEST"
Docker给了我一个异常,说-e exec command not found.
然而,如果我改变dockerfile使用ENTRYPOINT而不是CMD, -e标志工作,但web服务器不启动。
我在这里错过了什么吗?ENTRYPOINT是否被重写了?
编辑:所以我已经更新了我的dockerfile使用ENTRYPOINT ["bash","/usr/share/nginx/html/runfile.sh", ";", " nginx -g daemon off;"]
但是docker容器仍然关闭。我是不是漏掉了什么?
NGINX 1.19在根目录下有一个/docker-entrypoint.d
文件夹,用来存放docker-entrypoint.sh
脚本执行的启动脚本。您还可以在日志中读取执行情况。
/docker-entrypoint.sh:/docker-entrypoint。D/不是空的,是会的尝试执行配置
/docker-entrypoint.sh/docker-entrypoint.d/
/docker-entrypoint.sh:推出
[..........]
/docker-entrypoint.sh:配置完成;准备启动
对于我自己和其他人,这是如何在启动时设置变量替换(对于nginx,也可能适用于其他图像):
我还写了一篇更深入的博客文章:https://danielhabenicht.github.io/docker/angular/2019/02/06/angular-nginx-runtime-variables.html
Dockerfile:
FROM nginx
ENV TEST="Hello variable"
WORKDIR /etc/nginx
COPY ./substituteEnv.sh ./substituteEnv.sh
# Execute the subsitution script and pass the path of the file to replace
ENTRYPOINT ["./substituteEnv.sh", "/usr/share/nginx/html/index.html"]
CMD ["nginx", "-g", "daemon off;"]
replace .sh:(与@Daniel West的回答相同)
#!/bin/bash
if [[ -z $1 ]]; then
echo 'ERROR: No target file given.'
exit 1
fi
#Substitute all environment variables defined in the file given as argument
envsubst ''$TEST '$UPSTREAM_CONTAINER '$UPSTREAM_PORT' < $1 > $1
# Execute all other paramters
exec "${@:2}"
现在可以运行docker run -e TEST="set at command line" -it <image_name>
catch是WORKDIR
,没有它nginx命令将无法执行。如果您想将此应用于其他容器,请确保相应地设置WORKDIR
。
如果你想在多个文件中递归地进行替换,这就是你要找的bash脚本:
# Substitutes all given environment variables
variables=( TEST )
if [[ -z $1 ]]; then
echo 'ERROR: No target file or directory given.'
exit 1
fi
for i in "${variables[@]}"
do
if [[ -z ${!i} ]]; then
echo 'ERROR: Variable "'$i'" not defined.'
exit 1
fi
echo $i ${!i} $1
# Variables to be replaced should have the format: ${TEST}
grep -rl $i $1 | xargs sed -i "s/'${$i}/${!i}/Ig"
done
exec "${@:2}"
NginX图像包含docker-entrypoint.d
,并且在容器启动时将查找位于那里的任何脚本。您可以在docker构建期间添加自定义脚本。我还发现,如果您使用的是alpine image,则没有安装bash,因此您可以通过运行:
RUN apk update
RUN apk upgrade
RUN apk add bash
样本DockerFile: FROM nginx:alpine
EXPOSE 443
EXPOSE 80
RUN apk update
RUN apk upgrade
RUN apk add bash
COPY ["my-script.sh", "/docker-entrypoint.d/my-script.sh"]
RUN chown nginx:nginx /docker-entrypoint.d/my-script.sh
USER nginx
为了限制自定义脚本的执行范围,强烈建议以非特权用户身份运行容器。
我知道这是晚了,但我发现这个线程,而寻找一个解决方案,所以我想我分享。
我也有同样的问题。您的ENTRYPOINT脚本还应该包含exec "$@"
#!/bin/sh
set -e
envsubst ''$CORS_HOST '$UPSTREAM_CONTAINER '$UPSTREAM_PORT' < /srv/api/default.conf > /etc/nginx/conf.d/default.conf
exec "$@"
这将意味着启动CMD从nginx:alpine
容器将运行。上述脚本将把指定的环境变量注入到配置文件中。通过在运行时这样做,您可以覆盖环境变量。
在dockerfile中按如下方式更新CMD行。请注意,如果runfile.sh
没有成功(exit 0;
在其中),那么下一个nginx
命令将不会执行。
FROM nginx
COPY . /usr/share/nginx/html
CMD /usr/share/nginx/html/runfile.sh && nginx -g 'daemon off;'
nginx docker文件使用CMD命令在您使用的基本映像上启动服务器。当您在dockerfile中使用CMD命令时,您会覆盖其映像中的CMD命令。正如dockerfile文档中提到的:
一个Dockerfile中只能有一个CMD指令。如果您列出多个CMD,则只有最后一个CMD生效。
nginx容器已经定义了ENTRYPOINT。如果你也定义了CMD,它会像"ENTRYPOINT CMD"一样将它们组合在一起,这样CMD就变成了ENTRYPOINT的参数。这就是为什么你需要重新定义ENTRYPOINT来让它工作。
通常ENTRYPOINT是这样定义的,如果你也传递CMD,它将由ENTRYPOINT脚本执行。然而,这可能不是每个容器的情况。
- 如何使用phaser使html5游戏在移动设备浏览器上运行
- 使用压缩的JavaScript文件(不是运行时压缩)
- Javascript运行php文件,然后下载文件
- chrome扩展:尽管运行了at:documentidle,js脚本还是过早启动
- 我已经创建了一个jquery转盘,并使用if条件来运行和停止转盘
- Angularjs代码未在匿名函数中运行
- jquery设置为使用参数运行
- 如何根据时间运行不同的脚本
- Meteor方法在客户端返回null,在客户端运行的相同方法返回正确的值
- 将文本框链接到由按钮运行的javascript公式
- 为什么不是't运行此Javascript的Chrome
- ng应用程序使脚本无限运行
- 是否可以从 Firefox 运行 bash 脚本?(使用 Firefox 附加组件 SDK)
- 如何使用MozillaRhino中文件的重定向输入来运行bash脚本的Command()
- 在NGINX docker容器中启动前运行bash脚本
- 通过node.js运行带有参数的Bash脚本
- 从客户端请求中使用Node运行Bash Script
- 从bash脚本运行javascript
- 从按钮html运行bash脚本
- 有一种方法来运行Node.js与Bash命令在Windows