zoukankan      html  css  js  c++  java
  • docker笔记2_原理解析和dockerfile简单理解

    上一页

    Docker 的镜像原理

    1. 镜像是一种轻量级、可执行的独立软件包,用来打包运行环境和基于运行环境开发的软件,它包含运行某个软件所需的所有内容,包括代码,运行时,库,环境变量和配置文件。

    2. 官方解释

    UnionFS(联合文件系统):Union文件系统(UnionFS)是一种分层、轻量级并且高性能的文件系统,它支持对文件系统的修改作为一次提交来一层层的叠加,同时可以将不同目录挂载到同一个虚拟文件系统下(unite several directories into a single virtual filesystem)。Union 文件系统是 Docker 镜像的基础。镜像可以通过分层来进行继承,基于基础镜像(没有父镜像),可以制作各种具体的应用镜像。
    
    特性:一次同时加载多个文件系统,但从外面看起来,只能看到一个文件系统,联合加载会把各层文件系统叠加起来,这样最终的文件系统会包含所有底层的文件和目录
    

    镜像加载原理

    1. Docker镜像加载原理:

    1. docker的镜像实际上由一层一层的文件系统组成,这种层级的文件系统UnionFS。
    2. bootfs(boot file system)主要包含bootloader和kernel, bootloader主要是引导加载kernel, Linux刚启动时会加载bootfs文件系统,在Docker镜像的最底层是bootfs。这一层与我们典型的Linux/Unix系统是一样的,包含boot加载器和内核。当boot加载完成之后整个内核就都在内存中了,此时内存的使用权已由bootfs转交给内核,此时系统也会卸载bootfs。
    3. rootfs (root file system) ,在bootfs之上。包含的就是典型 Linux 系统中的 /dev, /proc, /bin, /etc 等标准目录和文件。rootfs就是各种不同的操作系统发行版,比如Ubuntu,Centos等等。
    4. 平时我们安装进虚拟机的CentOS都是好几个G,为什么docker这里才200M??
    • 对于一个精简的OS,rootfs可以很小,只需要包括最基本的命令、工具和程序库就可以了,因为底层直接用Host的kernel,自己只需要提供 rootfs 就行了。由此可见对于不同的linux发行版, bootfs基本是一致的, rootfs会有差别, 因此不同的发行版可以公用bootfs。

    2. 为什么要采用分层结构?

    1. 最大的好处就是共享资源

    特点:

    • Docker镜像都是只读的
      当容器启动时,一个新的可写层被加载到镜像的顶部。
      这一层通常被称作“容器层”,“容器层”之下的都叫“镜像层”。

    Docker镜像commit操作补充

    1. docker commit 提交容器副本使之成为一个新的镜像
    2. docker commit -m=“提交的描述信息” -a=“作者” 容器ID 要创建的目标镜像名:[标签名]

    案例演示

    1. 从Hub上下载tomcat镜像到本地并成功运行
      • docker run -it -p 8080:8080 tomcat
        1. -p 主机端口:docker容器端口
        2. -P 随机分配端口
        3. i:交互
        4. t:终端

    docker 的容器数据卷

    就是相当与移动硬盘

    1. 是什么

    • 有点类似redis 里面的rdb 和aof文件

    2. 能干什么

    • 卷就是目录或文件,存在于一个或多个容器中,由docker挂载到容器,但不属于联合文件系统,因此能够绕过Union File System提供一些用于持续存储或共享数据的特性:
      1. 数据卷可在容器之间共享或重用数据
      2. 卷中的更改可以直接生效
      3. 数据卷中的更改不会包含在镜像的更新中
      4. 数据卷的生命周期一直持续到没有容器使用它为止
    1. 容器的持久化
    2. 容器间继承 + 共享数据

    3. 数据卷

    1. 直接命令添加

    • 命令
      • docker run -it -v /宿主机绝对路径目录:/容器内目录 镜像名
    • 查看数据卷是否挂载成功
      • docker inspect 容器ID
    • 容器和宿主机之间的数据共享
    • 容器停止退出后,主机修改后数据是否同步
      • 开机会自动同步
    • 命令带权限
      • docker run -it -v /宿主机绝对路径目录:/容器内目录:ro 镜像名

    Dockerfile 添加

    镜像模板的描述文件,特定docekr的编写方法

    1. 根目录下新建mydocker文件夹并进入
    2. 可在Dockerfile中使用VOLUME指令来给镜像添加一个或多个数据卷
    3. File构建
    4. build后生成镜像
      1. 获得一个新镜像zzyy/centos
    5. run容器
    6. 通过上述步骤,容器内的卷目录地址已经知道对应的主机目录地址哪??
    7. 主机对应默认地址
    上面的命令不能一对多,所以需要下面这个
    mkdir mydocekr
    
    vim Dockerfile
        # volume test
        FROM centos
        VOLUME ["/dataVolumeContainer1","/dataVolumeContainer2"]
        CMD echo "finished,--------success1"
        CMD /bin/bash
        
    docker build -f /mydocker/dockerfile -t firewine/centos1
    
    docker run -it firewine/centos1
    
    **如果没有指定,会自动生成相对应的地址**
    
    
    • Docker挂载主机目录Docker访问出现cannot open directory .: Permission denied
      • ++解决办法:在挂载目录后多加一个–privileged=true参数即可++

    4. 数据卷容器

    通俗来说:就是活动硬盘上面加活动硬盘,实现数据传递和依赖

    总体介绍

    1. 以上一步新建的镜像Firewine/centos为模板并运行容器dc01/dc02/dc03
    2. 它们已经具有容器卷
      • /dataVolumeContainer1
      • /dataVolumeContainer2

    容器间传递共享(–volumes-from)

    1. 先启动一个父容器dc01
      docker run -it --name dc01 firewine/centos
      
      1. 在dataVolumeContainer2新增内容
    2. dc02 /dc03 继承dc01
      docker run -it --name dc02 --volumes-from dc01 zzyy/centos
      
      • 继承 并且也是相互共享
    3. 回到dc01可以看到02/03各自添加的都能共享了
    4. 删除dc01,dc02修改后dc03可否访问
    5. 删除dc02后dc03可否访问
    6. 新建dc04继承dc03后再删除dc03
    7. 结论:容器之间配置信息的传递,数据卷的生命周期一直持续到没有容器使用它为止

    dockerFile 的解析

    通过这个文件,可以build 获得一个自定义的镜像

    1. dockerfile 是什么

    1. dockerfile

      • 是用来构建Docker镜像的构建文件,是由一系列命令和参数构成的脚本
    2. 构建三步骤

      • 编写dockerfile 文件
      • docker build
      • docker run
    3. 文件什么样

      FROM scratch
      MAINTAINER The CentOS Project <cloud-ops@centos.org>
      ADD c68-docker.tar.xz /
      LABEL name="CentOS Base Image" 
      vendor="CentOS" 
      license="GPLv2" 
      build-date="2016-06-02"
      
      # Default command
      CMD ["/bin/bash"]
      

    2. DockerFile构建过程解析

    1. dockerfile 内容基础知识

    1. 每条保留字指令都必须为大写字母且后面要跟随至少一个参数
    2. 指令按照从上到下,顺序执行
    3. #表示注释
    4. 每条指令都会创建一个新的镜像层,并对镜像进行提交

    2. Docker执行Dockerfile的大致流程

    1. docker从基础镜像运行一个容器
    2. 执行一条指令并对容器作出修改
    3. 执行类似docker commit的操作提交一个新的镜像层
    4. docker再基于刚提交的镜像运行一个新容器
    5. 执行dockerfile中的下一条指令直到所有指令都执行完成

    三个区别

    1. Dockerfile,需要定义一个Dockerfile,Dockerfile定义了进程需要的一切东西。Dockerfile涉及的内容包括执行代码或者是文件、环境变量、依赖包、运行时环境、动态链接库、操作系统的发行版、服务进程和内核进程(当应用进程需要和系统服务和内核进程打交道,这时需要考虑如何设计namespace的权限控制)等等;

    2. Docker镜像,在用Dockerfile定义一个文件之后,docker build时会产生一个Docker镜像,当运行 Docker镜像时,会真正开始提供服务;

    3. Docker容器,容器是直接提供服务的

    3. DockerFile体系结构(保留字指令)

    1. FORM
      • 基础镜像,当前新镜像是基于哪个镜像的
    2. MAINTAINER
      • 镜像维护者的姓名和邮箱地址
    3. RUN
      • 容器构建时需要运行的命令
    4. EXPOSE
      • 当前容器对外暴露出的端口
    5. WORKDIR
      • 指定在创建容器后,终端默认登陆的进来工作目录,一个落脚点
    6. ENV
      • 用来在构建镜像过程中设置环境变量
    7. ADD
      • 将宿主机目录下的文件拷贝进镜像且ADD命令会自动处理URL和解压tar压缩包
    8. COPY
      • 类似ADD,拷贝文件和目录到镜像中。
        将从构建上下文目录中 <源路径> 的文件/目录复制到新的一层的镜像内的 <目标路径> 位置
    9. VOLUME
      • 容器数据卷,用于数据保存和持久化工作
    10. CMD
      • 指定一个容器启动时要运行的命令
      • Dockerfile 中可以有多个 CMD 指令,但只有最后一个生效,CMD 会被 docker run 之后的参数替换
    11. ENTRYPOINT
      • 指定一个容器启动时要运行的命令
      • ENTRYPOINT 的目的和 CMD 一样,都是在指定容器启动程序及参数
    12. ONBUILD
      • 当构建一个被继承的Dockerfile时运行命令,父镜像在被子继承后父镜像的onbuild被触发
    BUILD Both RUN
    FROM WORKDIR CMD
    MAINTAINER USER ENV
    COPY EXPOSE
    ADD VOLUME
    RUN ENTRYPOINF
    ONBUILD
    .dockerignore

    4. 案例

    1. mycentos

    1. 自动定义centos 支持 以下功能
      • 默认路径
      • vim
      • ifconfig
    from centos
    
    env mypath /usr/local
    workdir $mypath
    
    run yum -y install vim
    run yum -y install net-tools
    
    expose 80
    cmd echo "=======success------"
    cmd /bin/bash
    
    1. 构建镜像

      1. docker build -t 新镜像名字:TAG
    2. 列出镜像变更历史

      1. docker history 镜像名

    2. 自定义tomcat

    1. 新建一个目录

    2. 将jdk和tomcat的压缩包 copy进来

    3. 编写dockerfile文件

    4. build 一个新镜像

    5. 运行

      • docker run -d -p 9080:8080 --name myt9 -v /zzyyuse/mydockerfile/tomcat9/test:/usr/local/apache-tomcat-9.0.8/webapps/test -v /zzyyuse/mydockerfile/tomcat9/tomcat9logs/:/usr/local/apache-tomcat-9.0.8/logs --privileged=true zzyytomcat9
    6. 测试

    FROM centos
    MAINTAINER  author 
    #把宿主机当前上下文的c.txt拷贝到容器/usr/local/路径下
    COPY c.txt /usr/local/cincontainer.txt
    #把java与tomcat添加到容器中
    ADD jdk-8u171-linux-x64.tar.gz /usr/local/
    ADD apache-tomcat-9.0.8.tar.gz /usr/local/
    #安装vim编辑器
    RUN yum -y install vim
    #设置工作访问时候的WORKDIR路径,登录落脚点
    ENV MYPATH /usr/local
    WORKDIR $MYPATH
    #配置java与tomcat环境变量
    ENV JAVA_HOME /usr/local/jdk1.8.0_171
    ENV CLASSPATH $JAVA_HOME/lib/dt.jar:$JAVA_HOME/lib/tools.jar
    ENV CATALINA_HOME /usr/local/apache-tomcat-9.0.8
    ENV CATALINA_BASE /usr/local/apache-tomcat-9.0.8
    ENV PATH $PATH:$JAVA_HOME/bin:$CATALINA_HOME/lib:$CATALINA_HOME/bin
    #容器运行时监听的端口
    EXPOSE 8080
    #启动时运行tomcat
    # ENTRYPOINT ["/usr/local/apache-tomcat-9.0.8/bin/startup.sh" ]
    # CMD ["/usr/local/apache-tomcat-9.0.8/bin/catalina.sh","run"]
    CMD /usr/local/apache-tomcat-9.0.8/bin/startup.sh && tail -F /usr/local/apache-tomcat-9.0.8/bin/logs/catalina.out
    

    如果存在错误,请指出

  • 相关阅读:
    解题:HNOI 2008 玩具装箱
    2016级算法第一次上机助教版解题报告
    求解斐波那契数列复杂度分析
    数据库复习之规范化理论应用(第八次上机内容)
    数据库复习之规范化理论
    题目1042:Coincidence(最长公共子序列)
    题目1020:最小长方形(简单)
    题目1016:火星A+B(字符串拆分)
    题目1014:排名(结构体排序)
    题目1021:统计字符(hash简单应用)
  • 原文地址:https://www.cnblogs.com/YJBlog/p/10440697.html
Copyright © 2011-2022 走看看