基于Dockerfile创建镜像

Docker镜像的创建

1.基于现有镜像创建

//首先启动一个镜像,在容器里做修改
docker run -itd --name web centos:7 /bin/bash
#启动容器

docker exec -it web bash
#进入容器
 ​
yum install -y epel-release  #安装epel源
yum install -y nginx         #安装nginx
yum install net-tools        #安装tools工具
nginx                        #启动服务
netstat -natp |grep 80       #查看端口是否开启
 ​
docker ps -a                 #查看容器ID

//然后将修改后的容器提交为新的镜像,需要使用该容器的ID号创建新镜像
docker commit -m "new nginx" -a "xxxx" 容器id nginx:centos7
 #常用选项:
 -m 指定说明信息;
 -a 指定作者信息;
 -p 生成过程中停止容器的运行。
 c7f4bc905c29  原容器ID。
 nginx:centos  生成新的镜像名称。
 ​
docker images                                #查看生成的新镜像
docker run -itd nginx:centos7 bash           #使用新的镜像创建容器
docker ps -a                                 #查看容器状态
docker exec -it 容器id bash                  #进入容器
nginx                                        #启动nginx服务
netstat -natp |grep 80                       #查看80端口是否开启

2.基于本地模板创建

通过导入操作系统模板文件可以生成镜像,模板可以从OPENVZ 开源项目下载,下载地址为: openvz.org/ Download/template/precreated

模板里面就是使用docker export 命令导出的容器文件
 ​
#下载模板
wget http://download.openvz.org/template/precreated/debian-7.0-x86-minimal.tar.gz
 ​
#导入为镜像,两种方法
#方法一
cat debian-7.0-x86-minimal.tar.gz | docker import - debian:test

#方法二
docker import debian-7.0-x86-minimal.tar.gz -- debian:test
 ​
#查看镜像
docker images
 ​
#使用导入的镜像创建容器
docker run -itd debian:test bash
docker ps -a

3.基于Dockerfile创建

联合文件系统(UnionFS)

Union文件系统是Docker镜像的基础。镜像可以通过分层来进行继承,基于基础镜像(没有父镜像),可以制作各种具体的应用镜像。

特性:
一次同时加载多个文件系统,但从外面看起来,只能看到一个文件系统,联合加载会把各层文件系统叠加起来,这样最终的文件系统会包含所有底层的文件和目录。
我们下载的时候看到的一层层的就是联合文件系统。

镜像加载原理

Docker的镜像实际上由一层一层的文件系统组成,这种层级的文件系统就是UnionFS。

rootfs:
rootfs 是指 Docker 镜像中的根文件系统。
它包含了一个完整的文件系统,包括所有的文件和目录,以及与之相关的权限、所有权等信息。
在运行容器时,这个文件系统会被挂载到容器的根目录。

Docker 镜像是由一系列层(layers)组成的,每一层都包含文件系统的一部分。
这些层在逻辑上叠加在一起,形成最终的文件系统,而这个最终的文件系统就是 rootfs。
bootfs:
bootfs 是一个概念,通常用来描述 Docker 镜像中用于引导的文件系统。
引导文件系统是用于启动操作系统的文件系统,包含了启动时所需的核心文件等。
在 Docker 中,bootfs 可以看作是镜像中的一部分,它包含了启动容器所需的最基本的文件。

bootfs主要包含bootloader和kernel,bootloader主要是引导加载kernel,Linux刚启动时会加载bootfs文件系统。

在Docker镜像的最底层是bootfs,这一层 与我们典型的Linux/Unix系统是一样的, 包含boot加载器和内核。
当boot加载完成之 后整个内核就都在内存中了,此时内存的使用权已由bootfs转交给内核,此时系统也会卸载bootfs。
rootfs,在bootfs之上。包含的就是典型Linux系统中的/dev、/proc、/bin、/etc等标准目录和文件。
rootfs就是各种不同的操作系统发行版,比如Ubuntu, Centos等。

bootfs就是内核引导器(引导加载内核)和内核。

rootfs是n多个基础镜像(提供基础操作环境)和应用镜像叠加在一起的只读层。

运行的容器实例会在rootfs之上添加一个可读可写层。

容器中操作系统容量小的原因

因为对于精简的OS,rootfs可以很小, 只需要包含最基本的命令、工具和程序库就可以了,因为底层直接用宿主机的kernel,自己只需要提供rootfs就可以了。
由此可见对于不同的linux发行版,
bootfs基本是一 致的,rootfs会 有差别,因此不同的发行版可以公用bootfs。

大部分镜像是通用的,但如果专门基于某个版本创建的镜像,在其他版本的操作系统中运行可能会有问题。

Docker镜像结构的分层

  • (1)、Dockerfile中的每个指令都会创建一个新的镜像层;
  • (2)、镜像层将被缓存和复用;
  • (3)、当Dockerfile的指令修改了,复制的文件变化了,或者构建镜像时指定的变量不同了,对应的镜像层缓存就会失效;
  • (4)、某一层的镜像缓存失效,它之后的镜像层缓存都会失效;
  • (5)、镜像层是不可变的,如果在某一层中添加一个文件,然后在下一层中删除它,则镜像中依然会包含该文件,只是这个文件在Docker 容器中不可见了。

Dockerfile

1.Dockerfile概述

Docker镜像是一个特殊的文件系统,除了提供容器运行时所需的程序、库、资源、配置等文件外,还包含了一些为运行时准备的一些配置参数(如匿名卷、环境变量、用户等)。
镜像不包含任何动态数据,其内容在构建之后也不会被改变。 

镜像的定制实际上就是定制每一层所添加的配置、文件。
如果我们可以把每一层修改 安装、构建、操作的命令都写入一个脚本,用这个脚本来构建、定制镜像,那么镜像构建透明性的问题、体积的问题就都会解决。
这个脚本就是Dockerfile。

我们需要定制首己额外的需求时,只需在Docketlle上添加或者修改指令,重新生成image 即可,省去了敲命令的麻烦。
就是描述该层应当如何构建。有了Dockerfile,当我们需要定制自己额外的需求时,只需在Dockerfile上添加或者修改指令,重新生成image即可,省去了敲命令的麻烦。

除了手动生成Docker镜像之外,可以使用bockerfile自动生成镜像。
Dockerfile 是由多条的指令组成的文件,其中每条指令对应Linux中的一条命令Docker程序将读取Dockerfile中的指令生成指定镜像。

Dockerfile结构大致分为四个部分:

  • 基础镜像信息
  • 维护者信息
  • 镜像操作指令
  • 容器启动时执行指令

Dockerfile每行支持一条指令,每条指令可携带多个参数,支持使用以“#“号开头的注释。

Dockerfile其实就是我们用来构建Docker镜像的源码,当然这不是所谓的编程源码,而是一些命令的组合,只要理解它的逻辑和语法格式,就可以编写Dockerfile了。

Dockerfile的作用:
它可以让用户个性化定制Docker镜像。因为工作环境中的需求各式各样,网络上的镜像很难满足实际的需求。

2.Dockerfile常见命令

命令作用

FROM

image_name:tag

声明基础镜像

MAINTAINER

user_name

声明镜像的作者
ENV key value设置环境变量 (可以写多条)
RUN command编译镜像时运行的脚本(可以写多条)
CMD设置容器的启动命令
ENTRYPOINT设置容器的入口程序

ADD source_dir/file

dest_dir/file

将宿主机的文件复制到镜像内,如果是一个压缩文件,将会在复制后自动解压。支持URL路径下载源文件,但下载方式不能自动解压。

COPY source_dir/file

dest_dir/file

和ADD相似,将宿主机的文件复制到镜像内,但是如果有压缩文件并不能解压。不支持URL路径下载。
WORKDIR path_dir设置工作目录
ARG设置工作目录
VOLUMN设置容器的挂载卷

FROM

指定基础镜像信息,指定容器的操作系统

MAINTAINER

指定维护者信息(可有可无)

RUN

在基础的镜像上执行的命令,每个run就是一层,分层越多,镜像越大

ENTERPOINT

设置容器运行时的默认命令(容器内部运行的主程序)

CMD

指定容器运行时的默认命令(docker run /bin/bash后面加了其他的命令,cmd的指令将会被覆盖)

EXPOSE

暴露端口(指定容器的运行端口)

ENV

为后续指令设置环境变量环境变量可以被RUN命令使用(声明容器运行需要的环境变量)

ADD

复制,解压(解压不支持.zip和.rar,支持tar.gz和tar.bz2,支持url地址解析和复制)

  • ADD 的优点: 在执行 <源文件> 为 tar 压缩文件的话,压缩格式为 gzip、bzip2 以及 xz 的情况下,会自动复制并解压到 <目标路径>。
  • ADD 的缺点: 在不解压的前提下,无法复制 tar 压缩文件。会令镜像构建缓存失效,从而可能会令镜像构建变得比较缓慢。具体是否使用,可以根据是否需要自动解压来决定。

COPY

复制文件,不能解压,只能复制本地文件,文件要和dockerfile在一个目录(官方推荐复制用COPY)

VOLUME

创建一个容器内的挂载点,既可以为宿主机挂载,也可以拱容器挂载

USER

设置运行镜像时使用的用户或者UID(可以不加)

WORKDIR

为后续指令设置的工作目录

ONBUILD

这个镜像可以被其他镜像引用,需要这个命令

ARG

定义在Dockerfile中用于构建时由用户传递的变量;ARG 用于构建时的参数传递,
而 ENV 用于在容器运行时设置环境变量

3.ENTRYPOINT和CMD的区别

  • (1)、ENTRYPOINT设定容器启动时第一个运行的命令;
    CMD是启动容器时默认执行的命令,如果指定多条CMD命令,只执行最后一条命令。
  • (2)、ENTRYPOINT的指令不会被覆盖;
    而CMD的命令在构建镜像时,使用docker run 加上参数会覆盖CMD的指令。
  • (3)、CMD可以为ENTRYPOINT进行传参。
  • (4)、ENTERPOINT和CMD的指令都是在容器启动时执行,都会成为容器的主进程。主进程负责接收信号,处理容器的生命周期,主进程退出,容器也会终止运行。
[root@docker1 test]# cat dockerfile 
# Dockerfile

FROM centos:7
# 使用基础镜像

MAINTAINER "this is my docker <pup>"
# 设置作者信息

ENTRYPOINT ["echo","hello"]
# 使用 ENTRYPOINT 指令设置容器启动时执行的默认命令

CMD ["WORLD"]
# 使用 CMD 指令设置默认参数,这些参数会传递给 ENTRYPOINT 指令中的命令

docker build -t centos7:test .
docker run -it --name test centos7:test
#不要加d,否则会后台运行。

4.ADD和COPY的区别

(1)、共同点:
ADD和COPY都可以复制本地文件到镜像中。

(2)、区别:
ADD:如果是一个压缩文件,ADD会在复制后自动解压。且支持URL路径下载源文件,但URL下载和解压特性不能一起使用,任何压缩文件通过URL拷贝,都不会自动解压。COPY:如果是压缩文件,COPY并不能解压。且COPY只能复制本地文件,不支持URL路径拷贝。

5.RUN命令的优化

&&:
RUN ls /opt && yum -y insatll nginx
#&& 连接多个命令,确保前一个命令成功后才执行下一个命令

分号;:
使用分号可以在一行中连接多个命令,不管前一个命令是否成功,后面的命令都会被执行。
dockerfile
Copy code
RUN command1 ; command2 ; command3

双竖线 ||:
双竖线表示“或者”,如果前一个命令失败,才会执行后面的命令。
dockerfile
Copy code
RUN command1 || command2

反斜杠 \:
反斜杠可以用来将一行命令拆分成多行,提高可读性。相当于换行
dockerfile
Copy code
RUN command1 \
    && command2 \
    && command3

Dockfile实际应用

1.Dockfile源码编译Apache

FROM centos:7
MAINTAINER this is my  diy apache <pup>
RUN yum install -y gcc gcc-c++ make pcre pcre-devel expat-devel perl
ADD apr-1.6.2.tar.gz /opt/
ADD apr-util-1.6.0.tar.gz /opt/
ADD httpd-2.4.29.tar.bz2 /opt/
RUN mv /opt/apr-1.6.2 /opt/httpd-2.4.29/srclib/apr && mv /opt/apr-util-1.6.0 /opt/httpd-2.4.29/srclib/apr-util &&\
cd /opt/httpd-2.4.29/ &&\
./configure --prefix=/usr/local/httpd --enable-so --enable-rewrite --enable-charset-lite --enable-cgi &&\
make -j 4 && make install
EXPOSE 80
CMD ["/usr/local/httpd/bin/apachectl","-D","FOREGROUND"]
#-D FOREGROUND参数告诉服务器以前台模式运行,这样它就可以直接在终端的标准输出中显示日志信息。
否则容器启动之后会关闭,无法提供正常服务。

docker build -t apache:centos .
docker run -itd --name httpd1 -p 1314:80 apache:centos

2.Dockfile源码编译Nginx 

cd /opt
mkdir nginx
cd nginx
--上传nginx-1.22.0.tar.gz--
vim Dockerfile

FROM centos:7
MAINTAINER "this is my nginx <pup>"
RUN yum -y install gcc pcre-devel openssl-devel zlib-devel openssl openssl-devel
RUN useradd -M -s /sbin/nologin nginx
ADD nginx-1.22.0.tar.gz /opt/
RUN cd /opt/nginx-1.22.0/ &&\
./configure --prefix=/usr/local/nginx --user=nginx --group=nginx --with-http_ssl_module --with-http_v2_module --with-http_realip_module --with-http_stub_status_module --with-http_gzip_static_module --with-pcre --with-stream --with-stream_ssl_module --with-stream_realip_module &&\
make -j 4 && make install
EXPOSE 80
CMD ["/usr/local/nginx/sbin/nginx","-g","daemon off;"]

docker build -t nginx:centos .
docker run -itd --name nignx -p 1316:80 nginx:centos

3.镜像容量过大的解决方案 

  • (1)、基础镜像尽量使用轻量级最小化的镜像。
  • (2)、Dockerfile中尽量把RUN指令合并在一起,减少镜像的层数(因为每一个RUN指令就是一个镜像层)。
  • (3)、多级构建(拿Dockerfile构建好的镜像再构建一次)。

多级构建

#基层镜像
FROM centos:7 AS first
#镜像作者信息描述
MAINTAINER this is apache image <yh 2022-11-23 >
#指定的Linu执行脚本
RUN yum -y install gcc gcc-c++ make pcre pcre-devel expat-devel perl
#将源码编译的安装包安放到容器中并进行解压
ADD apr-1.6.2.tar.gz /opt/
ADD apr-util-1.6.0.tar.gz /opt/
ADD httpd-2.4.29.tar.bz2 /opt/
#进行源码编译安装
RUN mv /opt/apr-1.6.2 /opt/httpd-2.4.29/srclib/apr && mv /opt/apr-util-1.6.0 /opt/httpd-2.4.29/srclib/apr-util && cd /opt/httpd-2.4.29 && ./configure --prefix=/usr/local/httpd --enable-so --enable-rewrite --enable-charset-lite --enable-cgi && make -j 4 && make install
#二阶段构建
FROM centos:7
#将一阶段的已安装好的包安防到二阶端中,并舍弃一阶段的其他无用资源
COPY --from=first  /usr/local/httpd  /usr/local/httpd
#安装apache运行所需的环境依赖包,不再安装源码编译所需的依赖包
RUN yum install -y pcre pcre-devel expat-devel perl
EXPOSE 80
ENTRYPOINT ["/usr/local/httpd/bin/apachectl","-D","FOREGROUND"]

docker build -t apache1:centos .
docker run -itd --name httpd2 -p 1315:80 apache1:centos

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mfbz.cn/a/241108.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

共享门店会在未来新零售占据主角吗?

共享门店作为一种创新的商业模式&#xff0c;在未来新零售领域中可能会占据一定的角色&#xff0c;但具体是否会成为主角&#xff0c;还需要根据市场的发展和技术的进步来判断。 首先&#xff0c;共享门店模式通过资源共享、风险共担、客户共享和收益共享等方式&#xff0c;为…

Python 递归及目录遍历

递归调用&#xff1a;一个函数&#xff0c;调用了自身&#xff0c;称为递归调用 递归函数&#xff1a;一个会调用自身的函数 凡是循环能做的事&#xff0c;递归都能做。 目录 递归示例 普通方法实现 递归方式实现 计算分析&#xff1a; 递归遍历目录 引入os 遍历目录 执…

Unity | 渡鸦避难所-2 | 搭建场景并添加碰撞器

1 规范项目结构 上期中在导入一系列的商店资源包后&#xff0c;Assets 目录已经变的混乱不堪 开发过程中&#xff0c;随着资源不断更新&#xff0c;遵循一定的项目结构和设计规范是非常必要的。这可以增加项目的可读性、维护性、扩展性以及提高团队协作效率 这里先做下简单的…

【BigDecimal类—常用API系列】解决java浮点计算精度损失问题

文章目录 Java浮点计算精度损失问题BigDecimal进行精确运算的解决方案 Java浮点计算精度损失问题 BigDecimal它是干什么用的呢&#xff1f;什么是java浮点计算精度损失问题&#xff1f;我们先看一段代码&#xff0c;看这个代码有什么问题&#xff1f;再说BigDeimal这个类是干什…

【机器学习】亚马逊云科技基础知识:以推荐系统为例。你知道机器学习的关键所在么?| 机器学习管道的各个阶段及工作:以Amazon呼叫中心转接问题为例讲解

有的时候,暂时的失利比暂时胜利要好得多。 ————经典网剧《mao pian》,邵半仙儿 🎯作者主页: 追光者♂🔥 🌸个人简介: 💖[1] 计算机专业硕士研究生💖 🌿[2] 2023年城市之星领跑者TOP1(哈尔滨)🌿 🌟[3] 2022年度博客之星人工智能领域TOP

深入了解—C++11特性

目录 一、 C11简介 二、初始化列表 2.1 C98中{}的初始化问题 2.2 内置类型的列表初始化 2.3 自定义类型的列表初始化 2.3.1. 标准库支持单个对象的列表初始化 2.3.2. 多个对象的列表初始化 三、变量类型推导 3.1 为什么需要类型推导 3.2 decltype类型推导 3.2.1. 推…

方法-PC端远程调试分布式训练

本专栏为深度学习的一些技巧,方法和实验测试,偏向于实际应用,后续不断更新,感兴趣童鞋可关,方便后续推送 简介 一些简单的代码我们使用Pycharm本地调试就能运行成功&#xff0c;但在诸如使用GPU进行分布式训练和推断等场景中&#xff0c;由于我们本地的电脑没有GPU或者没有多…

慢SQL的治理经验

其他系列文章导航 Java基础合集数据结构与算法合集 设计模式合集 多线程合集 分布式合集 ES合集 文章目录 其他系列文章导航 文章目录 前言 一、慢SQL导致的后果 二、可能导致慢SQL的原因 三、如何发现慢SQL 3.1 JVM Sandbox 四、识别高危SQL 4.1 阿里的重点强制SQL规…

docker容器-compose单机容器编排

yaml文件&#xff1a;是一种标记语言&#xff0c;以竖列的形式展示序列化的数据格式&#xff0c;可读性高 类似于json格式&#xff0c;语法简单 yaml通过缩进来表示数据结构&#xff0c;连续的项目用-减号来表示 yaml文件使用的注意事项 1、大小写敏感 2、通过缩进表示层级…

VUE3语法--toRefs与toRef用法

1、功能概述 ref和reactive能够定义响应式的数据&#xff0c;当我们通过reactive定义了一个对象或者数组数据的时候&#xff0c;如果我们只希望这个对象或者数组中指定的数据响应&#xff0c;其他的不响应。这个时候我们就可以使用toRefs和toRef实现局部数据的响应。 toRefs是…

AntDB数据库致力降本增效的某省高速清分结算实践——优势总结和推广意义

中国正处于数字化转型的关键时期&#xff0c;高速公路正朝着智慧高速的建设迈进。不论是传统的传统高速卡口&#xff0c;诸如“数据采集、数据上传”和“数据处理”的基础建设1.0时代&#xff0c;还是不久将来即将实现的具备“车辆协同智能”、“边缘控制中心”及“智慧高速云控…

vue+element项目中页面多个接口异常,只提示一次异常信息

有时候一个页面会同时调多个接口&#xff0c;但是多个接口异常&#xff0c;需要做提示&#xff0c;那么提示的时候会弹出很多的提示信息&#xff0c;这无疑让体验感降低很多。 所以针对这种情况&#xff0c;我们配合element UI统一做一个异常状态的处理&#xff0c;只能显示一…

MATLAB实现图像变换和滤波

MATLAB实现图像变换和滤波方法对具有不同特征的灰度图像进行处理 图像变换方法包括&#xff1a;DFT及IDFT&#xff0c;DCT及IDCT 图像滤波方法包括低通滤波和高通滤波 图像变换 DFT/IDFT 图像一般是二维的&#xff0c;根据二维离散傅里叶变换公式DFT&#xff0c;可以将图片…

多线程案例-定时器(附完整代码)

定时器是什么 定时器是软件开发中的一个重要组件.类似于一个"闹钟".达到一个设定的时间之后,就执行某个指定好的代码. 定时器是一种实际开发中非常常用的组件. 比如网络通信种,如果对方500ms内没有返回数据,则断开尝试重连. 比如一个Map,希望里面的某个key在3s之后过…

视频播放插件ckplayer

地址&#xff1a;https://www.ckplayer.com/demo.html 效果图

events.out.tfevents文件信息提取

深度学习训练数据有时候是记录在log文件中&#xff0c;文件名类型为events.out.tfevents.xxx.king,当然这些文件可以通过tensorbord工具可视化&#xff0c;这里提供一些events.out.tfevents文件信息提取的方法。 &#xff08;1&#xff09;events.out.tfevents多个文件可视化 …

UniGui使用CSSUniTreeMenu滚动条

有些人反应UniTreeMenu当菜单项目比较多的时候会超出但是没有出滚动条&#xff0c;只需要添加如下CSS 老规矩&#xff0c;unitreemeu的layout的componentcls里添加bbtreemenu&#xff0c;然后在css里添加 .bbtreemenu .x-box-item{ overflow-y: auto; } 然后当内容超出后就会…

反射篇笔记

反射的本质&#xff1a;加载类。 把某个类的字节码文件加载到内存中。并允许以变成的方式解剖类中的各种成分&#xff08;成员方法&#xff0c;变量&#xff0c;构造器&#xff09;。 例如在使用IDEA时&#xff0c;他的提示&#xff0c;就是利用反射&#xff0c;提前将类中的…

AMEYA360:海康存储PCIe4.0固态硬盘A4000介绍

海康存储即将发布PCIe4.0固态硬盘新品A4000&#xff0c;搭载全新定制主控及高品质3D NAND闪存颗粒&#xff0c;最大顺序读取速度达7100MB/s&#xff0c;提供五年质保服务。 2022年&#xff0c;海康存储开始在PCIe 4.0固态硬盘领域全面发力&#xff0c;推出C4000 ECO、C4000等多…
最新文章