美文网首页
Docker三要素:镜像、仓库、容器

Docker三要素:镜像、仓库、容器

作者: 轻轻敲醒沉睡的心灵 | 来源:发表于2023-05-18 16:19 被阅读0次

    Docker学习中,有3个名词是要理解的:镜像-images、仓库-registry、容器-container。
    Docker作为一个软件,我们使用它,最终就是使用 docker生成的容器,也就是一个简单的linux系统及里面的软件。
    镜像,就像我们装系统时用到的Win7.ISO、Win10.ISO系统一样,是用来生成容器的,我们用到的软件,nginx、mysql、redis等都有对应的镜像。
    仓库,就是存放镜像的地方,我们可以从仓库下载所需的镜像。仓库有官方的仓库、阿里云的仓库等,我们也可以自己搭建私有仓库来存放镜像。
    容器:就像系统一样,里面有我们用到的东西,是使用镜像生成的。每一个容器都有对应的镜像,但是一个镜像可以重复使用生成多个容器。
    注意:如果一个镜像被用来生成容器了,那么这个镜像一般就不能被删除了,要等容器被删除后才能删除。

    1. 镜像

    是一种轻量级、可执行的独立软件包,它包含运行某个软件所需的所有内容,我们把应用程序和配置依赖打包好形成一个可交付的运行环境(包括代码、运行时需要的库、环境变量和配置文件等),这个打包好的运行环境就是image镜像文件。
    镜像存储在仓库中,我们可以直接用命令拉取,类似git:

    pull nginx
    我们可以看到,拉取nginx时,并不是一个文件,而是下载了6个文件,一层一层的。也就是docker镜像是分层的,这种分层的,我们称为联合文件系统

    1.1 联合文件系统

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

    1.2 镜像加载原理

    • docker的镜像实际上由一层一层的文件系统组成,这种层级的文件系统UnionFS。
    • bootfs(boot file system)主要包含bootloader和kernel, bootloader主要是引导加载kernel, Linux刚启动时会加载bootfs文件系统,在Docker镜像的最底层是引导文件系统bootfs。这一层与我们典型的Linux/Unix系统是一样的,包含boot加载器和内核。当boot加载完成之后整个内核就都在内存中了,此时内存的使用权已由bootfs转交给内核,此时系统也会卸载bootfs。
    • rootfs (root file system) ,在bootfs之上。包含的就是典型 Linux 系统中的 /dev, /proc, /bin, /etc 等标准目录和文件。rootfs就是各种不同的操作系统发行版,比如Ubuntu,Centos等等。
    分层
    • Docker镜像层都是只读的,容器层是可写的:当容器启动时,一个新的可写层被加载到镜像的顶部。这一层通常被称作“容器层”,“容器层”之下的都叫“镜像层”。所有对容器的改动 - 无论添加、删除、还是修改文件都只会发生在容器层中。只有容器层是可写的,容器层下面的所有镜像层都是只读的。


      容器层

    我们看一个Ubuntu的docker镜像:


    ubuntu

    大小只有72M,非常精简了,我们平时用的ubuntu是4G左右的,Server版也是2G左右的。
    对于一个精简的OS,rootfs可以很小,只需要包括最基本的命令、工具和程序库就可以了,因为底层直接用Host的kernel,自己只需要提供 rootfs 就行了。由此可见对于不同的linux发行版, bootfs基本是一致的, rootfs会有差别, 因此不同的发行版可以公用bootfs。

    1.3 镜像简单制作

    Docker中的镜像分层,支持通过扩展现有镜像,创建新的镜像。类似Java继承于一个Base基础类,自己再按需扩展。
    新镜像是从 base 镜像一层一层叠加生成的。每安装一个软件,就在现有镜像的基础上增加一层。

    分层叠加
    因此我们可以通过docker commit命令来简单制作我们需要的镜像。就用 刚才的 ubuntu镜像,加上vimip addr功能来制作新镜像。
      1. 启动原始镜像,进入:


        原始镜像

        可以看到这些功能不能使用。

      1. 安装软件

    安装脚本太多,写命令吧

    apt update
    apt install -y vim
    apt install -y iproute2
    

    这个时候,命令就可以用了


    安装完
      1. commit命令

    使用commit命令制作自己的镜像
    docker commit -m="新镜像的描述" -a="作者" 旧容器ID 新镜像名:[标签版本]

    查看ID
    docker commit -m="ubuntu add vim ipaddr" -a="zrb" e758c41ad2dd zrbubuntu:1.1
    
    制作完成
      1. 启动新镜像,测试


        测试

    注意:这里只是用commit命令制作简单的镜像,后面会写用Dockerfile做一些复杂镜像(包含jdk和我们写的jar等)。

    1.4 镜像上传仓库

    上面说了仓库分公共的的私有的,公共仓一般都是用的阿里云的,docker hub毕竟是国外的,网速慢啊。怎么上传阿里云仓库,阿里云上面有,需要注册账号,可以注册账号自己试试。

    阿里云
    这里说一下私有仓库,私有仓库需要我们自己搭建,使用官方提供的工具:Docker Registry
      1. 搭建私有仓库
    # 拉取
    sudo docker pull registry
    # 启动
    sudo docker run -d -p 5000:5000  -v /home/soft/myregistry/:/tmp/registry --privileged=true --name registry registry
    # 查看
    sudo docker ps
    

    查看私服仓库中镜像:

    curl -XGET http://192.168.50.89:5000/v2/_catalog
    
    私服镜像
      1. 规范镜像

    docker tag命令将要上传的镜像规范化。
    标准: docker tag 镜像:Tag Host:Port/Repository:Tag

    sudo docker tag  zrbubuntu:1.1  192.168.50.89:5000/zrbubuntu:1.1
    

    会生成新镜像的:


    规范的镜像
      1. 将私服地址添加到docker配置文件
    sudo vim /etc/docker/daemon.json
    # 添加,注意上行结尾的,要有,上一行是 阿里的加速器
    "insecure-registries": ["192.168.111.162:5000"]
    # 重启docker
    sudo systemctl restart docker
    
    配置
      1. 推送私服

    用上面规范好的 镜像格式

    # 推送
    sudo docker push 192.168.50.89:5000/zrbubuntu:1.1
    # 查看
    curl -XGET http://192.168.50.89:5000/v2/_catalog
    
    push
    这样别人就可以拉取并使用了。
    docker pull 192.168.50.89:5000/zrbubuntu:1.1

    2. 容器

    Docker 容器其实没什么难理解的,就是用 docker run 启动一个镜像,就会有容器了,但是在用命令启动的时候需要有几点注意的:

      1. 注意前后台启动,-d表示后台运行。-it是交互界面。
      1. 注意给容器起个名字,--name
      1. 注意端口映射:-p将用到的端口映射到宿主机
      1. 注意数据卷的绑定:-v将宿主机目录和容器内目录关联。主要作用2个:一是方便容器内软件使用自定义配置,一是容器内软件产生的数据可以备份到外面,安全。
      1. 可以设置容器内软件的环境变量:-e
      1. --net--ip设置网络

    用一个mysql的例子说一下:

    docker run -d \
    -p 3316:3306 \
    --privileged=true \
    -v /home/soft/mysql/log:/var/log/mysql \
    -v /home/soft/mysql/data:/var/lib/mysql \
    -v /home/soft/mysql/conf/my.cnf:/etc/mysql/my.cnf \
    -v /home/soft/mysql/mysql-files:/var/lib/mysql-files \
    -e MYSQL_ROOT_PASSWORD=mysql123 \
    -e TZ=Asia/Shanghai  \
    --name mysql \
    mysql:latest
    

    这个例子基本上都用到了,由于ip需要自定义网络才能设定,这先不设置了。
    注意:若进行数据卷绑定,添加上--privileged=true,这样是为了使用宿主机的root权限。

    试了一下,设置的密码生效:


    mysql

    相关文章

      网友评论

          本文标题:Docker三要素:镜像、仓库、容器

          本文链接:https://www.haomeiwen.com/subject/otwisdtx.html