背景
1.镜像是其他人提供的,修改镜像比较麻烦
2.镜像中的变量不足以满足当前业务
3.镜像中的启动命令不足以满足当前业务
覆盖前
Haskell
#通过以下命令,查看镜像中的参数和启动命令
docker inspect

镜像中的命令是写死的,需要覆盖调镜像中的命令
覆盖
由图中可以看到是一个sh命令,通过--entrypoint 找到入口,并在镜像之后修改
设置的命令必须在镜像名称之后
Haskell
docker run -d --network=host --name cName \
--entrypoint sh \
-e JAVA_OPTS="-Xms1024m -Xmx1024m -Dspring.profiles.active=dev -Dserver.port=5566 -Duser.timezone=GMT+8" \
-v /etc/hosts:/etc/hosts \
-v `pwd`:/apps/ \
-v /etc/localtime:/etc/localtime --restart=unless-stopped image:1.0 \
-c 'java -jar $JAVA_OPTS app.jar'
覆盖后

PS: 如果命令中
-c "java -jar $JAVA_OPTS "用了双引号,宿主机的 Shell 会先解析$JAVA_OPTS(宿主机没有这个环境变量,直接替换为空),容器内实际执行的是java -jar(只有空参数)---这个要注意(要是用单引号,才能使用前面使用的变量)
同时也可以是用--entrypoint java作为修改入口,比如在需要修改镜像中指定的jar路径和名称的时候,命令如下:
Haskell
docker run -d --network=host --name cName \
--entrypoint java \
-e JAVA_OPTS="-Xms1024m -Xmx1024m -Dspring.profiles.active=dev -Dserver.port=5566 -Duser.timezone=GMT+8" \
-v /etc/hosts:/etc/hosts \
-v `pwd`:/apps/ \
-v /etc/localtime:/etc/localtime --restart=unless-stopped image:1.0 \
-jar '$JAVA_OPTS app.jar'
这个时候,就仅会修改 java -jar之后的相关命令
完整的容器启动脚本
Haskell
#!/bin/bash
# 查询当前路径下 用jar结尾的文件并根据最后修改时间排序,获取文件名
#readonly c_name=$(ls *.jar -lt |head -n 1 | awk '{print substr($9,1,length($9)-4)}')
readonly c_name="容器名称"
readonly port=2233
readonly profiles_active=dev
readonly image_name="镜像版本"
docker_run(){
docker rm -f ${c_name} ;
docker run -d --network=host --name ${c_name} \
--entrypoint sh \
-e JAVA_OPTS="-Xms1024m -Xmx1024m -Dspring.profiles.active=${profiles_active} -Dserver.port=${port} -Duser.timezone=GMT+8" \
-e JAR_NAME="$1" \
-v /etc/hosts:/etc/hosts \
-v `pwd`:/apps/ \
-v /etc/localtime:/etc/localtime --restart=unless-stopped ${image_name} \
-c 'java -jar $JAVA_OPTS /apps/$JAR_NAME'
}
if [ -n "$1" ]; then
docker_run $1
else
echo "没有指定默认的启动jar包-执行按照最后修改时间的最后一个jar文件-->"$(ls *.jar -lt |head -n 1| awk '{print $9}')
docker_run $(ls *.jar -lt |head -n 1| awk '{print $9}')
fi
后记
遇到此问题多次,每次都没有顺手记录,导致需要不停的尝试,本次记录备查,需要注意的点:
1. 变量参数,要在指定镜像名称之前设置才能生效2.覆盖的命令必须在指定镜像之后才能生效
3.必须要要找到合适的覆盖入口
4.最后的命令想要使用之前的参数,需要使用单引号,不能使用双引号