使用Dockerfile来构建镜像
Dockerfile原理
关于Docker中使用Dockerfile来构建镜像,可以简单的理解为:将所有的操作都写在一个脚本中,这个脚本的名称就叫Dockerfile,执行构建镜像的命令时,就会去执行这个命令。
上面只是通俗的说法,其实,你写完Dockerfile之后,执行构建镜像的时候,并不是直接执行Dockerfile中命令,而是将这个文件所在目录的所有文件,都交给docker的守护进程,让docker守护进程来解析之后,再执行。
上面说的是将Dockerfile所在目录的所有文件,都交给守护进程,至于为什么要这样做,待会再解释。
但是,如果是初学Dockerfile,建议建立一个空的目录,在空目录中创建一个Dockerfile文件。
创建Dockerfile
-> ~ # mkdir TestDockerfile
-> ~ # cd TestDockerfile
-> TestDockerfile # touch Dockerfile
-> TestDockerfile # echo "hello world" > index.html #创建一个测试文件
Dockerfile实例
下面的Dockerfile会构建出一个安装有nginx和vim的docker镜像
#VERSION 0.0.1 FROM ubuntu:16.04 MAINTAINER ganlixin ubuntu "1355036599@qq.com" RUN apt-get update && apt-get install -y nginx RUN apt-get install -y vim RUN rm -rf /var/www/html/index.html ADD ./index.html /var/www/html/index.html WORKDIR /var/www/html RUN echo "hello docker" > demo.html WORKDIR /root RUN echo "hello root" > hey.txt ENV SELF_DEFINE_ENVIROMENT_VAR "123456789" RUN echo $SELF_DEFINE_ENVIROMENT_VAR > env_var.html USER root:root COPY index.html /tmp/test CMD /bin/bash EXPOSE 80
下面会针对这个Dockerfile中每一项,进行详细的说明。
Dockerfile指令
注释
在Dockerfile中,每一行“#”之后的内容,都会被当成注释。
一般用来写一些提示信息,比如版本信息,镜像说明
FROM
FROM ubuntu:16.04
表示使用当前Dockerfile在构建镜像时,是基于哪一个镜像。一般来说,不会从零开始构建镜像,一般都会选择一个已有的镜像作为基础,在上面安装各种软件,然后构建出一个加工过的镜像。
示例中,使用ubuntu:16.04作为基础
MAINTAINER
MAINTAINER beyond ubuntu ”1355036599@qq.com"
用来提示用户,这个Dockerfile的作者、以及作者的联系方式
RUN
RUN apt-get update && apt-get install -y nginx
RUN用来执行一条Linux命令,执行的时机:在构建镜像的时候。
不是在使用该镜像创建容器后,运行容器的时候。
一个Dockerfile文件中可以有多个RUN命令,也就是说,在构建镜像时,可以执行多个指定的命令
ADD
ADD ./index.html /var/www/html/index.html
还记得在创建Dockerfile的时候,创建了一个测试文件吗?他的内容是hello world,文件名是index.html
这个命令的作用就是将Dockerfile文件所在目录中的某个文件,添加到要构建的镜像中。
如果将Dockerfile所在的环境叫做外部环境,而构建出的镜像成为内部环境的话,ADD命令的作用就是将外部环境中的文件 添加到 内部环境中。
注意,目标路径,如果不是以 / 结尾,表示的文件;如果以 / 结尾,表示目录
WORKDIR
设置一个工作目录,后面的RUN命令、CMD命令都会在这个工作目录中执行。
相当于cd path
WORKDIR /var/www/html
RUN echo "hello docker" > demo.html
WORKDIR /root
RUN echo "hello root" > hey.txt
上面的代码表示,在/var/www/html目录下的demo.html中输入内容“hello world”;
然后切换工作目录,在/root目录中,在hey.txt中输入内容,“hello root”
ENV
定义环境变量,相当于全局变量
ENV SELF_DEFINE_ENVIROMENT_VAR "123456789"
在镜像中设置一个环境变量,SELF_DEFINE_ENVIROMENT_VAR ,值为123456789
之后可以使用$SELF_DEFINE_ENVIROMENT_VAR来使用这个变量
USER
指定启动容器后,是以什么身份来运行,可以同时设置组和用户
USER root:root
表示启动容器后,是以root组的root身份运行
COPY
COPY命令和ADD命令功能类似,
COPY index.html /tmp/test
将外部环境的index.html拷贝到内部环境/tmp目录下,重命名为test。如果是要将index.html拷贝到/tmp/test目录下,即,将test看作是目录,那么,就要在test后面加 / ,即 /tmp/test/
注意,目标路径,如果不是以 / 结尾,表示的文件;如果以 / 结尾,表示目录
CMD
CMD /bin/bash
表示在使用镜像,启动容器的时候,会运行的命令。
和RUN的区别:
1、RUN是在构建镜像的时候运行,而CMD是在容器启动的时候运行。可以理解为,RUN命令只是在构建时执行一次,而CMD命令在每次启动容器时,都会执行一次。
2、一个Dockerfile中可以有多个RUN命令,多个RUN命令都会执行;而CMD命令虽然可以出现多次,但是只有最后一个会被执行。
3、RUN命令只运行一次,所以说不存在命令覆盖的情况,而CMD会出现命令覆盖的情况(即第2点区别),在启动容器时,如果指定了要执行的命令,那么Dockerfile中的CMD命令同样会被覆盖。
EXPOSE
EXPOSE 80,表示将容器的80端口,映射到外部环境(宿主机)的某个端口上。
可以通过启动容器的时候指定映射到宿主机的哪个端口
构建Docker镜像
使用命令docker build命令即可触发构建操作,但是需要注意,构建时,要指定构建出的镜像名称(使用-t选项)以及tag,以及Dockerfile所在的路径。
一般构建的时候,都是进入到Dockerfile所在的目录
假设现在使用前面的Dockerfile构建一个镜像,镜像名为beyond/test,标签为v1,则执行如下命令
-> ~ # cd TestDockerfile
-> TestDockerfile # docker build -t="beyond/test:v1" .
.......等待
........
.......构建完成
-> TestDockerfile # docker run -i -t --name first_test beyond/test
root@38ff683ba587:~# #进入到容器中
注意,此时,在运行容器的时候,并没有在后面加上/bin/bash,这是因为Dockerfile中CMD命令已经指定了在启动容器时执行的命令。
测试
现在我们逐个检查Dockerfile中的操作是否成功,即,看对应操作的结果是否保留下来
1、看/var/www/html/index.html这个文件的内容是不是hello world
2、看/var/www/html下面是不是有一个demo.html,内容为hello docker
3、看/root目录下hey.txt的内容是不是hello root
4、使用env命令,看是不是有SELF_DEFINE_ENVIROMENT_VAR这个环境变量
5、看/root目录下env_var.html的内容是不是环境变量SELF_DEFINE_ENVIROMENT_VAR的值123456789
6、看一下/tmp/test文件内容是不是hello world
指定宿主机和容器的端口映射
-> TestDockerfile # docker run -d --name second_test -p 8080:80 beyond/test:v1 nginx -g "daemon off;"
7d74273277cc925ae5656591367c5b3cc6e4b9ed90d251123eeaed42b463367c
外部访问你的ip:8080,然后就可以看到结果了。
使用Dockerfile来构建镜像的更多相关文章
- Docker:dockerfile自动构建镜像 [六]
一.手动docker镜像的缺点 相对于手动制作的docker镜像,使用dockerfile构建的镜像有以下优点: 1.dockerfile只有几kb,便于传输 2.使用dockerfile构建出来的镜 ...
- Docker系列(三)Dockerfile 离线构建镜像
一.Dockfile介绍: Dockfile是一种被Docker程序解释的脚本,Dockerfile由一条一条的指令组成,每条指令对应Linux下面的一条命令.Docker程序将这些Dockerfil ...
- Dockerfile减少构建镜像大小的方法
这几天基于Dockerfile构建应用需要的特殊的镜像,比如Nginx需要add很多module的,就需要在镜像内编译和做build. 通过Dockerfile构建镜像时,很容易把镜像构建得很大. 从 ...
- 013、Dockerfile构建镜像(2019-01-02 周三)
参考https://www.cnblogs.com/CloudMan6/p/6830067.html Dockerfile构建镜像过程分析 root@docker-lab:~/111# ls ...
- Dockerfile制作自定义镜像
本文介绍最精简的Dockerfile文件构建镜像,Docker启动的时候可以启动一个shell脚本 1.首先编写Dockerfile文件 说明 1.启动的这个shell脚本一定是不退出的,比如服务器的 ...
- Docker、Dockerfile、Docker镜像、容器这些都是什么鸟?
老生常谈,再再再……普及一下: Docker:最早是dotCloud公司出品的一套容器管理工具,但后来Docker慢慢火起来了,连公司名字都从dotCloud改成Docker. Dockerfile: ...
- docker学习笔记(2) 构建镜像
一.手动构建一个简单镜像 我们以构建nginx的docker镜像为例:手动构建镜像 docker pull centos 安装基础镜像docker run --name mynginx -it ...
- Dockerfile 构建镜像 - 每天5分钟玩转容器技术(13)
Dockerfile 是一个文本文件,记录了镜像构建的所有步骤. 第一个 Dockerfile 用 Dockerfile 创建上节的 ubuntu-with-vi,其内容则为: 下面我们运行 dock ...
- 使用Dockerfile构建镜像-Docker for Web Developers(5)
1.理解Dockerfile语法 语法命令 命令功能 举例 FROM 所有的dockerfile都必须以FROM命令指定镜像基于哪个基础镜像来制作 FROM ubuntu:14:04 MAINTAIN ...
随机推荐
- PHP is much better than you think
Rants about PHP are everywhere, and they even come from smart guys.When Jeff Atwood wrote yet anothe ...
- 注册mySQL到JDBC驱动程序方法浅谈
一.注册方法(4种) 1)服务提供者框架: 符合JDBC 4.0规范的驱动程序包含了一个文件META-INF/services/java.sql.Driver,在这个文件中提供了JDBC驱动实现的类名 ...
- 【Teradata System】How Teradata uses MPP Systems
内存分配 内存初始化时将分配给操作系统和Vprocs,内存不使用部分的90%做为FSG (File Segment Cache) ,由PDE对FSG进行管理. FSG Cache:缓存常驻内存的dat ...
- ZooKeeper Observers解决节点过多时写性能下降问题
ZooKeeper Observers Observers: Scaling ZooKeeper Without Hurting Write Performance How to use Observ ...
- dp 动态规划 蘑菇
蘑菇真的贵,友情价更高 Description 由于提莫为巡逻准备的蘑菇太多了,多余的蘑菇路上种不下,于是他精心挑选了一些蘑菇拜访他的好朋友小炮 提莫的蘑菇一共有n个,对于编号为i的蘑菇魔力值是a ...
- TortoiseHg 学习笔记
0.前言 TortoiseHg是分布式的源代码管理工具Mercurial的GUIclient. mercurial 作为3大主流的分布式源代码管理工具.已经被广泛的使用.比如 googleco ...
- Oracle使用数据泵 (expdp/impdp)实施迁移
实验环境: 1.导出环境:RedHat6.4+Oracle 11.2.0.4.0,利用数据库自带的scott示例用户进行试验测试. Directory:wjq à /tmp/seiang_wjq 2. ...
- SkylineGlobe for web开发是否支持IE11?
之前有客户反馈,说在IE11里浏览skyline开发的系统页面,会提示错误,怀疑是不是skyline不支持IE11了,其实不是. 主要是因为IE11更加遵循W3C规范,所以IE11与低版本IE在加载a ...
- 使用sql语句比较excel中数据的不同
使用sql语句比较excel中数据的不同 我所在的项目组是一套物流系统,负责与公司的电商系统进行对接.但是公司的电商系统的省市区的配置和物流系统的省市区的配置有差异,所以需要找到这些差异. 首先找到我 ...
- C# - Span 全面介绍:探索 .NET 新增的重要组成部分
假设要公开特殊化排序例程,以就地对内存数据执行操作.可能要公开需要使用数组的方法,并提供对相应 T[] 执行操作的实现.如果方法的调用方有数组,且希望对整个数组进行排序,这样做就非常合适.但如果调用方 ...