
由于相关需求,现有的docker制作的jdk镜像是Java8早期版本的镜像,在安全性上存在较大的问题,所以计划对docker依赖的系统以及jdk进行升级操作。这其中遇到了一些问题,不过都顺利的圆满解决了,下面来具体聊一聊细节把
docker制作JDK镜像选型
为了减小容器的体积,所以考虑使用alpine的镜像,这次选择alpine没有做版本相关的限制,考虑最新版本的镜像在安全性上会有一个较大的提升,目前经过阿里云的安全扫描,相关漏洞的个数为0;
JDK选择的也是JDK8的最新长期支持版,JDK8相对来说目前使用比较广泛,而且稳定性较高。
docker制作JDK第一版的过程
由于alpine镜像作为极小型的Linux容器,它的运行环境是没法直接运行JDK的,所以需要新增一些依赖来进行相关兼容,在此过程中安装了glibc-2.31-r0.apk,该包在Github上下载的,由于服务器带宽较低,所以下载速度奇慢,所以自己将对应的包下载下来,放到了腾讯云的COS上供自己下载使用。
下面是第一版Dockerfile的内容
| 12
 3
 4
 5
 6
 7
 8
 9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 
 | FROM alpine:latest
 MAINTAINER dislazy2019@outlook.com
 
 RUN  echo http://mirrors.aliyun.com/alpine/v3.7/main > /etc/apk/repositories && \
 echo http://mirrors.aliyun.com/alpine/v3.7/community >> /etc/apk/repositories
 
 RUN apk update && apk upgrade
 
 RUN wget -q -O /etc/apk/keys/sgerrand.rsa.pub https://cdn.songbo.fun/sgerrand.rsa.pub && \
 wget https://cdn.songbo.fun/glibc-2.31-r0.apk && \
 apk add glibc-bin-2.31-r0.apk
 
 
 ADD jdk1.8.0_231 /usr/local
 ENV JAVA_HOME=/usr/local/jdk1.8.0_231
 ENV CLASSPATH=$JAVA_HOME/bin
 ENV JRE_HOME=/usr/local/jdk1.8.0_231/jre
 ENV PATH=$JAVA_HOME/bin:$PATH
 CMD ["java","-version"]
 
 
 | 
在上面的镜像中,只安装了运行JDK所需要的相关包以及将JDK放到了容器文件中,其实在此之前有一步是需要对JDK进行内容的删减,删减一些多余的JAR包和介绍文件,来达到减少容器体积的目的。
时区问题
JDK镜像制作成功后,很顺利的推到了阿里云的镜像仓库中,并且迅速进行服务的打包部署,一切都进行的很顺利,服务也正常运行并启动。
后来在查看日志的过程中,发现服务运行日志的时差达到了8个小时,马上想到了没设置正确的时区,导致Java运行获取的当地时间不正确,这问题在生产中是致命的,然后迅速进行第二次镜像升级改造,本次主要正确设置了时区,使Java进行按照本地时间运行。
下面是第二版Dockerfile的内容
| 12
 3
 4
 5
 6
 7
 8
 9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 
 | FROM alpine:latest
 MAINTAINER dislazy2019@outlook.com
 
 RUN  echo http://mirrors.aliyun.com/alpine/v3.7/main > /etc/apk/repositories && \
 echo http://mirrors.aliyun.com/alpine/v3.7/community >> /etc/apk/repositories
 
 RUN apk update && apk upgrade && ln -sf /usr/share/zoneinfo/Asia/Shanghai /etc/localtime && echo "Asia/Shanghai" > /etc/timezone
 
 RUN wget -q -O /etc/apk/keys/sgerrand.rsa.pub https://cdn.songbo.fun/sgerrand.rsa.pub && \
 wget https://cdn.songbo.fun/glibc-2.31-r0.apk && \
 apk add glibc-bin-2.31-r0.apk
 
 
 ADD jdk1.8.0_231 /usr/local
 ENV JAVA_HOME=/usr/local/jdk1.8.0_231
 ENV CLASSPATH=$JAVA_HOME/bin
 ENV JRE_HOME=/usr/local/jdk1.8.0_231/jre
 ENV PATH=$JAVA_HOME/bin:$PATH
 CMD ["java","-version"]
 
 | 
上面的镜像设置了时区文件,顺利解决了时区的问题。
编码问题
作为一个程序员,对乱码这个一定会异常的敏感,在大学计算机的课堂上,对于这个问题始终会强调,编码问题是数据可读性的重要保障,一个不慎,可能全盘皆输。
问题的发现比较偶然,因为我平常在工作中养成的工作习惯是日志基本使用英文,能不使用中文尽量不使用,所以一直没发现中文编码存在问题,后来因为接入了美团Cat,想试试告警效果,然后发现相关告警发送到企业微信的时候发现是乱码,此时才想到没有对乱码问题进行及时设置,此时有了第三版本的JDK镜像。
下面是第三版本的Dokcerfile
| 12
 3
 4
 5
 6
 7
 8
 9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 
 | FROM alpine:latest
 MAINTAINER dislazy2019@outlook.com
 
 RUN  echo http://mirrors.aliyun.com/alpine/v3.7/main > /etc/apk/repositories && \
 echo http://mirrors.aliyun.com/alpine/v3.7/community >> /etc/apk/repositories
 
 RUN apk update && apk upgrade && ln -sf /usr/share/zoneinfo/Asia/Shanghai /etc/localtime && echo "Asia/Shanghai" > /etc/timezone
 
 RUN wget -q -O /etc/apk/keys/sgerrand.rsa.pub https://cdn.songbo.fun/sgerrand.rsa.pub && \
 wget https://cdn.songbo.fun/glibc-2.31-r0.apk && \
 wget https://cdn.songbo.fun/glibc-bin-2.31-r0.apk && \
 wget https://cdn.songbo.fun/glibc-i18n-2.31-r0.apk && \
 apk add glibc-bin-2.31-r0.apk glibc-i18n-2.31-r0.apk glibc-2.31-r0.apk
 #复制本地编辑的locale.md
 COPY ./locale.md /locale.md
 #此时设置utfu编码
 RUN cat locale.md | xargs -i /usr/glibc-compat/bin/localedef -i {} -f UTF-8 {}.UTF-8
 
 ADD jdk1.8.0_231 /usr/local
 ENV JAVA_HOME=/usr/local/jdk1.8.0_231
 ENV CLASSPATH=$JAVA_HOME/bin
 ENV JRE_HOME=/usr/local/jdk1.8.0_231/jre
 ENV PATH=$JAVA_HOME/bin:$PATH
 ENV LANG=en_US.UTF-8
 ENV LANGUAGE=en_US.UTF-8
 CMD ["java","-version"]
 
 | 
为了加快镜像的构建速度,所以把必要的jar包都放到了腾讯云的COS上,以便于快速下载以及备份。
其中locale.md文件内容如下,有些不必要用到的我都给移除掉了,能大大节省镜像的构建速度
| 12
 3
 4
 5
 6
 7
 8
 9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 
 | el_CYel_GR
 en_AG
 en_AU
 en_BW
 en_CA
 en_DK
 en_GB
 en_HK
 en_IE
 en_IN
 en_NG
 en_NZ
 en_PH
 en_SG
 en_US
 en_ZA
 en_ZM
 en_ZW
 es_AR
 es_BO
 es_CL
 es_CO
 es_CR
 es_CU
 es_DO
 es_EC
 es_ES
 es_GT
 es_HN
 es_MX
 es_NI
 es_PA
 es_PE
 es_PR
 es_PY
 es_SV
 es_US
 es_UY
 es_VE
 et_EE
 eu_ES
 zh_CN
 zh_HK
 zh_SG
 zh_TW
 zu_ZA
 
 | 
该问题比较经典,在github上也有解决方案,主要原因就是alpine镜像本身原因没有对一些需要的特性需要支持,顺利解决了时区问题以及乱码问题,服务目前平稳运行,可以大大松口气。
结束语
以前用别人制作好的JDK镜像,发现很香,很多问题都不需要去考虑,直接拿来就用。
在自己制作并投入使用的时候会出现很多状况,所以我们制作镜像前后最好先了解一下有哪些坑,提前发现并且避免掉,这样才能减少错误,快速做好镜像。