一、注意事项

项目应用在完成开发后,应按照Docker镜像管理的规范要求进行应用镜像的打包, 镜像的打包应该注意一下几个问题:

  1. 需要注意基础镜像的选择。选择基础镜像两个标准原则:标准化和精简化。在选择基础镜像时应该是Docker官方发布的基础镜像。
  2. 注意业务进程的启动方式。在容器化时,需要将业务进程放在前台运行,当业务进程由于某种原因停止时,容器也容易销毁,便于进行故障问题定位与解决。
  3. 进程日志的输出问题。 在物理机运行应用进程时,通常将程序的日志输出到指定的文件中,便于日志分析和问题定位。在容器化后,需要根据公司业务日志处理平台进行容器日志的规划设计,如日志直接输出至前端(在宿主机下/var/lib/docker/id/*-json.log),或者挂载宿主机目录,将日志输出至宿主机目录下。
  4. 文件操作问题。Docker镜像采用的是联合文件系统,若频繁的进行I/O操作性能比较低,此时可以使用Volume将频繁的操作映射到宿主机上。
    由于Docker镜像分层的特性, 一般使用分层进行Docker镜像构建,底层操作系统,然后添加应用运行所需的依赖环境,再添加应用安装,如:

image.png

二、镜像制作流程

制作镜像的标准流程如下:

  1. 基础镜像选择 (如:Alpine,CentOS,Ubuntu,Debian,scratch)
  2. 基础镜像优化:
    软件包数据源设置(如yum的repo)
    安装网络工具等软件包
    时区设置
  3. 安装应用运行环境
    根据不同应用安装不同的运行环境, 如JDK,Python,GO,Nodejs
  4. 安装应用
    环境变量设置
    工作目录设置
    运行用户设置
    日志目录设置
    端口暴露

    三、相关示例

    为方便镜像管理,可以按照系统类型,环境类型以及项目进行创建目录,分类,如下:
    image.png
    本示例基于Alpine基础镜像制作java项目业务镜像。

    3.1 Base镜像制作

    (1)下载Alpine基础镜像
    下载官方Alpine镜像,并上传至私有仓库

    1. [root@jenkins home]# docker pull alpine
    2. Using default tag: latest
    3. latest: Pulling from library/alpine
    4. Status: Downloaded newer image for alpine:latest
    5. docker.io/library/alpine:latest
    6. [root@jenkins home]# docker images
    7. REPOSITORY TAG IMAGE ID CREATED SIZE
    8. alpine latest 7731472c3f2a 2 days ago 5.61MB
    9. [root@jenkins alpine]# docker tag alpine:latest docker.harbor.com/system/alpine:latest
    10. [root@jenkins alpine]# docker push docker.harbor.com/system/alpine:latest
    11. The push refers to repository [docker.harbor.com/system/alpine]
    12. c04d1437198b: Pushed
    13. latest: digest: sha256:d0710affa17fad5f466a70159cc458227bd25d4afb39514ef662ead3e6c99515 size: 528

    (2)基于Alpine镜像制作Base镜像

  1. 3docker build命令执行,并push至私有仓库
  2. ```bash
  3. [root@jenkins alpine_glibc]# docker build . -t docker.harbor.com/system/alpine-glibc:v1
  4. [root@jenkins alpine_glibc]# docker images
  5. REPOSITORY TAG IMAGE ID CREATED SIZE
  6. docker.harbor.com/system/alpine-glibc v1 efadec0848d4 4 seconds ago 62MB
  7. docker.harbor.com/system/alpine 3.13.0 7731472c3f2a 4 days ago 5.61MB
  8. docker.harbor.com/system/alpine latest 7731472c3f2a 4 days ago 5.61MB
  9. alpine latest 7731472c3f2a 4 days ago 5.61MB
  10. [root@jenkins alpine_glibc]# docker push docker.harbor.com/system/alpine-glibc:v1

3.2 运行环境镜像制作

(1)上传所需的jdk软件包

[root@jenkins alpine_glibc]# cd /home/dockerimages/env/jdk/alpine_jdk8/  
[root@jenkins alpine_jdk8]# pwd  
/home/dockerimages/env/jdk/alpine_jdk8  
[root@jenkins alpine_jdk8]# ls  
Dockerfile  jdk-8u271-linux-x64.tar.gz  
[root@jenkins alpine_jdk8]#

(2)Dockerfile文件编写

## 解压jdk 软件包,删除不需要的文件,减小文件体积,再重新打包:
[root@jenkins alpine_jdk8]# ls  
Dockerfile  jdk1.8.0_271  jdk-8u271-linux-x64.tar.gz  
[root@jenkins alpine_jdk8]# tar czf jdk1.8.0_271.tgz jdk1.8.0_271/  
[root@jenkins alpine_jdk8]# ls -lh  
total 235M  
-rw-r--r-- 1 root  root  1.4K Jan 18 11:40 Dockerfile  
drwxr-xr-x 8 10143 10143   93 Jan 18 11:44 jdk1.8.0_271  
-rw-r--r-- 1 root  root   98M Jan 18 11:55 jdk1.8.0_271.tgz  
-rw-r--r-- 1 root  root  137M Jan 18 10:45 jdk-8u271-linux-x64.tar.gz
## Dockerfile文件内容
[root@jenkins alpine_jdk8]# cat Dockerfile  
FROM  docker.harbor.com/system/alpine-glibc:v1  
MAINTAINER zkc "12345@qq.com"  
#指定工作目录  
WORKDIR /usr/local/java    
ADD jdk1.8.0_271.tgz /usr/local/java/        
ENV JAVA_HOME=/usr/local/java/jdk1.8.0_271  
ENV CLASSPATH=.:$JAVA_HOME/jre/lib/ext:$JAVA_HOME/lib/dt.jar:$JAVA_HOME/lib/tools.jar  
ENV PATH=$JAVA_HOME/bin:$PATH

(3)jdk镜像创建与上传测试

[root@jenkins alpine_jdk8]# docker build . -t docker.harbor.com/env/alpine-jdk:v8u271 
[root@jenkins alpine_jdk8]# docker images
REPOSITORY                              TAG       IMAGE ID       CREATED          SIZE
docker.harbor.com/env/alpine-jdk        v8u271    71193eb3a923   49 seconds ago   281MB
docker.harbor.com/system/alpine-glibc   v1        efadec0848d4   24 minutes ago   62MB
docker.harbor.com/system/alpine         3.13.0    7731472c3f2a   4 days ago       5.61MB
docker.harbor.com/system/alpine         latest    7731472c3f2a   4 days ago       5.61MB
alpine
## 上传镜像仓库
[root@jenkins alpine_jdk8]# docker push docker.harbor.com/env/alpine-jdk:v8u271
## 验证
[root@jenkins alpine_jdk8]# docker run -itd --name jdk8 docker.harbor.com/env/alpine-jdk:v8u271  
[root@jenkins alpine_jdk8]# docker ps
CONTAINER ID   IMAGE                                     COMMAND     CREATED         STATUS         PORTS     NAMES
1aa1a1e0cd7b   docker.harbor.com/env/alpine-jdk:v8u271   "/bin/sh"   8 minutes ago   Up 8 minutes             jdk8 
[root@jenkins alpine_jdk8]# docker exec -it jdk8 /bin/sh
/usr/local/java # java -version
java version "1.8.0_271"
Java(TM) SE Runtime Environment (build 1.8.0_271-b09)
Java HotSpot(TM) 64-Bit Server VM (build 25.271-b09, mixed mode)  
/usr/local/java

3.3 业务应用镜像制作

以eureka注册中心项目为例:
将编译好的Eureka的jar包放置在与Docker相同目录下,Dockerfile文件内容如下:

[root@jenkins eureka]# cat Dockerfile  
FROM docker.harbor.com/env/alpine-jdk:v8u271  
MAINTAINER zkc "12345@qq.com"  
#指定工作目录  
WORKDIR /usr/local/java  
VOLUME /tmp  
#上传项目jar文件  
COPY eureka-service.jar /usr/local/java/  
# 暴露端口  
    EXPOSE 8888  
#指定变量,后期k8s可用  
CMD java –jar  -Deureka.instance.hostname=${MY_POD_NAME}.eureka.ms eureka-service.jar        

##构建镜像  
[root@jenkins eureka]# docker build . -t docker.harbor.com/project/eureka-server:v1  
[root@jenkins eureka]# docker images  
REPOSITORY                                TAG       IMAGE ID       CREATED       SIZE  
docker.harbor.com/project/eureka-server   v1        5e590085da01   2 hours ago   328MB  
docker.harbor.com/env/alpine-jdk          v8u271    71193eb3a923   3 hours ago   281MB  
docker.harbor.com/system/alpine-glibc     v1        efadec0848d4   4 hours ago   62MB  
docker.harbor.com/system/alpine           3.13.0    7731472c3f2a   4 days ago    5.61MB  
docker.harbor.com/system/alpine           latest    7731472c3f2a   4 days ago    5.61MB  
alpine                                    latest    7731472c3f2a   4 days ago    5.61MB        

## 项目测试  
[root@jenkins eureka]# docker run -itd --name eureka-server -e MY_POD_NAME=eureka-server-1 -p 8888:8888 docker.harbor.com/project/eureka-server:v1  
b592eb5a6cb661cec16d27a4a11c3de95681f1542158760e7d6bad6ae0deb7da  
[root@jenkins eureka]# docker ps -a  
CONTAINER ID   IMAGE                                        COMMAND                  CREATED         STATUS         PORTS                    NAMES  
b592eb5a6cb6   docker.harbor.com/project/eureka-server:v1   "/bin/sh -c 'java -j…"   5 seconds ago   Up 5 seconds   0.0.0.0:8888->8888/tcp   eureka-server  
1aa1a1e0cd7b   docker.harbor.com/env/alpine-

image.png