如果对Docker还不是很了解的同学可以先看一下我之前的文章Docker基础教程(1)
定制镜像的两种方式
将容器打包成镜像
容器和镜像之间是可以互相转变的,镜像可以运行成容器,容器也可以打包成镜像,可以将所有数据打包起来,原封不动的变成一个镜像 首先了解一下打包的命令docker commit docker commit :从容器创建一个新的镜像。 -a :提交的镜像作者; -c :使用Dockerfile指令来创建镜像; -m :提交时的说明文字; -p :在commit时,将容器暂停。 * 参数后拼接容器名(或容器id) 自定义镜像名称:tag
我们利用docker commit
命令 来尝试打包一个镜像
[root@iZbp1cwfb0i1aften1twtvZ ~]# docker commit -a "zhai" -m "mytestcentos" mycentos mytestcentos:1.0
sha256:f336e3692c24837df716f1cb9379e29672f6baa5126df5e6d2ee4dda296beb22
输入docker images
查看已经打包好的镜像
[root@iZbp1cwfb0i1aften1twtvZ ~]# docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
mytestcentos 1.0 f336e3692c24 7 seconds ago 220 MB
这样就把一个正在运行的容器打包成镜像拉
利用Dockerfile来自定义创建镜像
什么是Dockerfile
Dockerfile是一个包含用于组合映像的命令的文本文档。可以使用在命令行中调用任何命令。 Docker通过读取Dockerfile中的指令自动生成镜像。
首先熟悉一下Dockerfile中的几个关键字 包括FROM、MAINTAINER、RUN、CMD、EXPOSE、ENV、ADD、COPY、ENTRYPOINT、VOLUME、USER、WORKDIR、ONBUILD等13个指令,我会选一些常用的关键字逐个解析
FROM
- 指定基础镜像,指你需要拓展的基础的镜像,比如你想运行一个自己的spring boot项目,需要的基础环境为java8,那么基础镜像可以指定为java:8
- tag或digest是可选的,如果不使用这两个值时,会使用lastest版本的基础镜像
WORKDIR
- 格式:WORKDIR /path/to/workdir
- 工作目录,类似于cd命令,通过WORKDIR设置工作目录后,Dockerfile中其后的命令RUN、CMD、ENTRYPOINT、ADD、COPY等命令都会在该目录下执行。在使用docker run运行容器时,可以通过-w参数覆盖构建时所设置的工作目录。
ADD
- 格式:
- ADD ...
- ADD ["",... ""] 用于支持包含空格的路径
- 将本地文件添加到容器中,tar类型文件会自动解压(网络压缩资源不会被解压),可以访问网络资源,类似wget
- 示例:
- ADD hom* /mydir/ # 添加所有以"hom"开头的文件
- ADD hom?.txt /mydir/ # ? 替代一个单字符,例如:"home.txt"
- ADD test relativeDir/ # 添加 "test" 到 `WORKDIR`/relativeDir/
- ADD test /absoluteDir/ # 添加 "test" 到 /absoluteDir/
COPY
- 与ADD关键字几乎相同,COPY不能添加网络资源,也不会自动解压文件
EXPOSE
- 格式:EXPOSE [...]
- 示例: EXPOSE 80 443
- EXPOSE并不会让容器的端口访问到主机。要使其可访问,需要在docker run运行容器时通过-p来发布这些端口,或通过-P参数来发布EXPOSE导出的所有端口
ENV
- 格式:EVN key value 。
- 用于指定环境变量,这些环境变量,后续可以被RUN指令使用,容器运行起来之后,也可以在容器中获取这些环境变量。
- 例如
ENV word hello
RUN echo $word
RUN
- shell执行
- 格式:RUN <Command>
- exec执行
- 格式: RUN ["executable", "param1", "param2"]
- RUN用于在构建镜像时中执行命令
- 注意:该命令是在构建镜像时既执行,并非创建容器时执行,执行时机不同
CMD
- 格式与RUN几乎相同
- CMD可以写为["param1","param2"]这种参数形式来作为ENTRYPOINT的参数
- 构建容器后调用,也就是在容器启动时才进行调用。
ENTRYPOINT
- 格式与RUN相同
- 配置容器,使其可执行化。配合CMD可省去"application",只使用参数。
- ENTRYPOINT与CMD非常类似,不同的是通过docker run执行的命令不会覆盖ENTRYPOINT,而docker run命令中指定的任何参数,都会被当做参数再次传递给ENTRYPOINT。Dockerfile中只允许有一个ENTRYPOINT命令,多指定时会覆盖前面的设置,而只执行最后的ENTRYPOINT指令。
CMD与ENTRYPOINT的异同
相同点: 只能写一条,如果写了多条,那么只有最后一条生效 容器启动时才运行,运行时机相同
不同点: ENTRYPOINT不会被运行的command覆盖,而CMD则会被覆盖 如果我们在Dockerfile种同时写了ENTRYPOINT和CMD,并且CMD指令不是一个完整的可执行命令,那么CMD指定的内容将会作为ENTRYPOINT的参数
注: Docker容器需要一直挂载一个命令,所以作为ENTRYPOINT或者CMD或者command都需要一直保持在前台运行,否则容器一启动就会立刻退出
接下来我们动手写一个自己的Dockerfile
首先找到一个文件夹创建一个叫Dockerfile的文件
[root@iZbp1cwfb0i1aften1twtvZ /]# cd /tmp/centos/
[root@iZbp1cwfb0i1aften1twtvZ centos]# ls
test.txt
[root@iZbp1cwfb0i1aften1twtvZ centos]# touch Dockerfile
可以看到这个文件夹还有我们上次测试留下的test.txt文件,我们就先不扔了,可以测试一下添加文件的效果.
接下来我们在Dockerfile中加入以下内容
FROM centos #根镜像为centos
ADD test.txt /tmp/ # 添加test.txt文件进入tmp文件夹
ADD http://images.xiaoazhai.com/qiaoben.jpg /tmp/qiaoben.jpg# 添加网络资源
ENV profile=test #指定环境变量
RUN echo mytest > /tmp/test.txt #测试RUN命令
RUN echo $profile # 测试环境变量是否成功
ENTRYPOINT top # 执行一个一直在前台运行的命令
EXPOSE 8999# 暴露端口
保存并退出 运行命令docker build -t mycentos:1.0 .
来打包成镜像,该命令中-t 指定打包出来的镜像名称 "."表示Dockerfile所在的文件夹
[root@iZbp1cwfb0i1aften1twtvZ centos]# docker build -t mycentos:1.0 .
Sending build context to Docker daemon 3.072 kB
Step 1/8 : FROM centos
---> 0f3e07c0138f
Step 2/8 : ADD test.txt /tmp/
---> e81cb238f74a
Removing intermediate container 90009ab9814e
Step 3/8 : ADD http://images.xiaoazhai.com/qiaoben.jpg /tmp/qiaoben.jpg
Downloading [==================================================>] 14.46 kB/14.46 kB
---> 0d4678989698
Removing intermediate container ea16c9215ed4
Step 4/8 : ENV profile test
---> Running in ec23237b9c5c
---> c6b43c68a91e
Removing intermediate container ec23237b9c5c
Step 5/8 : RUN echo mytest > /tmp/test.txt
---> Running in 6f276d45a876
---> 9a4094e0cc21
Removing intermediate container 6f276d45a876
Step 6/8 : RUN echo $profile
---> Running in 14c1b307c7bc
test
---> 4bb58acd03d4
Removing intermediate container 14c1b307c7bc
Step 7/8 : ENTRYPOINT top
---> Running in 528c78987148
---> 245601488490
Removing intermediate container 528c78987148
Step 8/8 : EXPOSE 8999
---> Running in 72433b0025e1
---> 238c588a72cf
Removing intermediate container 72433b0025e1
Successfully built 238c588a72cf
运行docker images
查看自己的镜像
root@iZbp1cwfb0i1aften1twtvZ centos]# docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
mycentos 1.0 238c588a72cf 5 minutes ago 220 MB
这里我就不跑起来了,有兴趣的同学可以自行跑通镜像,查看结果.
上传自己的镜像到DockerHub
首先需要注册一个DockerHub的账号点此注册
注册好以后运行docker login
输入账号密码登陆
[root@iZbp1cwfb0i1aften1twtvZ centos]# docker login
Login with your Docker ID to push and pull images from Docker Hub. If you don't have a Docker ID, head over to https://hub.docker.com to create one.
Username: yourname
Password:
Login Succeeded
接下来给我们的镜像改个名字 改成你的id+名称 运行docker tag docker tag mycentos:1.0 yourname/mycentos:1.0
[root@iZbp1cwfb0i1aften1twtvZ centos]# docker tag mycentos:1.0 602122993/mycentos:1.0
[root@iZbp1cwfb0i1aften1twtvZ centos]# docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
602122993/mycentos 1.0 238c588a72cf 16 minutes ago 220 MB
mycentos 1.0 238c588a72cf 16 minutes ago 220 MB
运行docker push 602122993/mycentos:1.0
将镜像推送到我们的dockerhub仓库(推送可能比较慢)
[root@iZbp1cwfb0i1aften1twtvZ centos]# docker push 602122993/mycentos:1.0
The push refers to a repository [docker.io/602122993/mycentos]
62bea31d0469: Pushed
3120fc785846: Pushed
8e2a2d912053: Pushed
9e607bb861a7: Mounted from library/centos
1.0: digest: sha256:58dd5bb4570b17e1730ee0ef3d1e2f88f7b84c114bb719dd580b2230abe2312b size: 1152
接下来我们删除本地的镜像并且拉取线上的镜像
[root@iZbp1cwfb0i1aften1twtvZ centos]# docker rmi mycentos:1.0
Untagged: mycentos:1.0
Untagged: 602122993/mycentos@sha256:58dd5bb4570b17e1730ee0ef3d1e2f88f7b84c114bb719dd580b2230abe2312b
[root@iZbp1cwfb0i1aften1twtvZ centos]# docker rmi 602122993/mycentos:1.0
Untagged: 602122993/mycentos:1.0
Deleted: sha256:238c588a72cf697c57aa39c670e5317d7fd732f7d18090933f8b747f746e3ebd
Deleted: sha256:245601488490345ca2c112f4f6e07b7e213da5029db5eba7f0a926c0a78e2d15
Deleted: sha256:4bb58acd03d44324bebea0b0ba56201b630a5eb59465b5ec668b433408cc3ef0
Deleted: sha256:9a4094e0cc217b1470f43d5b111c39e2a620b044a8122e819a34db226e6fb296
Deleted: sha256:5acf5ffaf5d260d38ccd8a4d97f601bd410ccb5ede7dc6f99ba6d587bed72be2
Deleted: sha256:c6b43c68a91e71295c3dc0b9fd4d9e439be36f8d25ddf0e73d5e7ab96ab41a3b
Deleted: sha256:0d4678989698e022d0001d53d608c98edccb401ea9c6fb7452116438cb03483e
Deleted: sha256:cd5d444402cdbfd1cab3e723353f066bb31b369712006eb9ec5e0fc0a711f97b
Deleted: sha256:e81cb238f74acdf9d31fc5e7945c64d0557b7fd2fb871bd9cf385c5d84d39f2b
Deleted: sha256:74e061523d05623c8021d35edd58c1e2484daed9b50252720f2a26fe91e3ed71
[root@iZbp1cwfb0i1aften1twtvZ centos]# docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
docker.io/centos latest 0f3e07c0138f 2 weeks ago 220 MB
[root@iZbp1cwfb0i1aften1twtvZ centos]# docker pull 602122993/mycentos:1.0
Trying to pull repository docker.io/602122993/mycentos ...
1.0: Pulling from docker.io/602122993/mycentos
729ec3a6ada3: Already exists
3d9879b8dfbb: Pull complete
f4c8ced9c934: Pull complete
4a9350bbacbe: Pull complete
Digest: sha256:58dd5bb4570b17e1730ee0ef3d1e2f88f7b84c114bb719dd580b2230abe2312b
Status: Downloaded newer image for docker.io/602122993/mycentos:1.0
这样我们就将我们自己创建的镜像上传到dockerhub上面啦~
感谢阅读
有兴趣可以关注我的个人微信公众号,会定期推送关于Java的技术文章,而且目前不恰饭都是干货哈哈哈哈