0x00 导航

  • 0x01 获取镜像
  • `docker image pull`
  • 0x02 查看镜像
  • `docker image ls`
  • `docker image tag`
  • `docker image inspect`
  • `docker image history`
  • 0x03 搜寻镜像
  • `docker search`
  • 0x04 删除和清理镜像
  • `docker image rm`
  • `docker image prune`
  • 0x05 创建镜像
  • `docker container commit `
  • `docker image import`
  • `docker image build`
  • 0x06 存出和载入镜像
  • `docker image save`
  • `docker image load`
  • 0x07 上传镜像
  • `docker image pull`


本章主要说了下Docker关于镜像相关的操作,相较来说还比较全面,但是说实在的,docker用起来的,比书上写的简单多了。官网上非常非常详细,详细到我没有耐心看完所有的,主要是感觉够用了。好了,正式开始。。。


0x01 获取镜像

镜像是运行容器的前提,官方的Docker hub网站中提供了非常多的镜像供我们使用。

docker实战入门 docker技术入门实战_centos


我们可以直接在上面进行搜索想使用已经制作好的镜像,比如centos

docker实战入门 docker技术入门实战_docker_02


从上面看出一共有5W+关于centos的镜像,这里我们选择用的最多,stars最多的第一个镜像,点进去。

docker实战入门 docker技术入门实战_镜像_03


可以看到最新镜像的版本以及各种历史版本信息,那我们下载的话,就可以使用pull命令进行拉取镜像了。

docker image pull

#语法:docker [image] pull image名字[:TAG]

[root@localhost ~]# docker pull centos
Using default tag: latest	
latest: Pulling from library/centos
7a0437f04f83: Pull complete 
Digest: sha256:5528e8b1b1719d34604c87e11dcd1c0a20bedf46e83b5632cdeac91b8c04efc1
Status: Downloaded newer image for centos:latest
docker.io/library/centos:latest

由于在上面没有指明[:TAG],所以默认下载的就是最新的版本,即lastst
注,另外中间的image关键字也是可以省略的。接下来再pull一个centos7镜像,具体的版本号在之前说过的hub.docker.com中搜索时可以看到。

[root@localhost ~]# docker image pull centos:7
7: Pulling from library/centos
2d473b07cdd5: Pull complete 
Digest: sha256:0f4ec88e21daf75124b8a9e5ca03c37a5e937e0e108a255d890492430789b60e
Status: Downloaded newer image for centos:7
docker.io/library/centos:7

这次指定了tag同时也加上了image关键字,效果是一样的,看大家以后的习惯了。

还可以拉取仓库下的所有镜像

[root@localhost ~]# docker image pull -a centos

0x02 查看镜像

下载好了以后,可以使用查看本地已经下载好的镜像

[root@localhost ~]# docker image ls
REPOSITORY    TAG       IMAGE ID       CREATED         SIZE
centos        latest    300e315adb2f   8 weeks ago     209MB
centos        7         8652b9f0cb4c   2 months ago    204MB
hello-world   latest    bf756fb1ae65   13 months ago   13.3kB

或者使用下面的命令也可以
[root@localhost ~]# docker images
REPOSITORY    TAG       IMAGE ID       CREATED         SIZE
centos        latest    300e315adb2f   8 weeks ago     209MB
centos        7         8652b9f0cb4c   2 months ago    204MB
hello-world   latest    bf756fb1ae65   13 months ago   13.3kB

解释下上面的几个关键字代表的含义

  • REPOSITORY仓库名称,其实这里指的是镜像名称
  • TAG则为具体的版本号
  • IMAGE ID代表了镜像,这个很重要,用他来指明镜像比使用名称来得更加方便,也是惟一id。
  • CREATED代表创建镜像的日期
  • SIZE则代表镜像大小。

这里重点说下SIZE这个地方,这里看起来每个镜像都占了不少空间,但是由于使用了unionfs联合文件系统,实际上docker都是分层储存的,不同镜像如果有相同的层,那么他们是可以共用的。看下面的例子:

下载mysql时是需要下载全部文件的

docker实战入门 docker技术入门实战_centos_04


下载完成后,再次下载mysql5.7

docker实战入门 docker技术入门实战_docker实战入门_05


可以发现有很多层都不需要下载了,他们共享同一个相同的层,这样docker的存储空间利用率就很高。可以使用下列命令进行查看:

[root@localhost ~]# docker system df  
TYPE            TOTAL     ACTIVE    SIZE      RECLAIMABLE
Images          5         0         1.273GB   1.273GB (100%)
Containers      0         0         0B        0B
Local Volumes   0         0         0B        0B
Build Cache     0         0         0B        0B
[root@localhost ~]# docker image ls 
REPOSITORY    TAG       IMAGE ID       CREATED         SIZE
mysql         5.7       a70d36bc331a   2 weeks ago     449MB
mysql         latest    c8562eaf9d81   2 weeks ago     546MB
centos        latest    300e315adb2f   8 weeks ago     209MB
centos        7         8652b9f0cb4c   2 months ago    204MB
hello-world   latest    bf756fb1ae65   13 months ago   13.3kB

可以很明显的看到,通过docker system df看到的大小为1.27G,比下载的docker镜像总大小是小的多的。

所有的 Docker 镜像都起始于一个基础镜像层,当进行修改或增加新的内容时,就会在当前镜像层之上,创建新的镜像层。

举一个简单的例子,假如基于 Ubuntu Linux 16.04 创建一个新的镜像,这就是新镜像的第一层;如果在该镜像中添加 Python 包,就会在基础镜像层之上创建第二个镜像层;如果继续添加一个安全补丁,就会创建第三个镜像层。

该镜像当前已经包含 3 个镜像层,如下图所示(这只是一个用于演示的很简单的例子)。

docker实战入门 docker技术入门实战_docker_06


在添加额外的镜像层的同时,镜像始终保持是当前所有镜像的组合,理解这一点非常重要。下图中举了一个简单的例子,每个镜像层包含 3 个文件,而镜像包含了来自两个镜像层的 6 个文件。

docker实战入门 docker技术入门实战_docker实战入门_07


上图中的镜像层跟之前图中的略有区别,主要目的是便于展示文件。下图中展示了一个稍微复杂的三层镜像,在外部看来整个镜像只有 6 个文件,这是因为最上层中的文件 7 是文件 5 的一个更新版本。

docker实战入门 docker技术入门实战_镜像_08


这种情况下,上层镜像层中的文件覆盖了底层镜像层中的文件。这样就使得文件的更新版本作为一个新镜像层添加到镜像当中。Docker 通过存储引擎(新版本采用快照机制)的方式来实现镜像层堆栈,并保证多镜像层对外展示为统一的文件系统。

docker实战入门 docker技术入门实战_mysql_09

这种文件系统称为unionfs联合文件系统。

顾名思义,unionFS可以把文件系统上多个目录(也叫分支)内容联合挂载到同一个目录下,而目录的物理位置是分开的。

要理解unionFS,我们首先要认识bootfsrootfs

  1. boot file system (bootfs):包含操作系统boot loader 和 kernel。用户不会修改这个文件系统。

一旦启动完成后,整个Linux内核加载进内存,之后bootfs会被卸载掉,从而释放出内存。

同样内核版本的不同的 Linux 发行版,其bootfs都是一致的。

  1. root file system (rootfs):包含典型的目录结构,包括 /dev, /proc, /bin, /etc, /lib, /usr, and /tmp

就是我下面这张图里的这些文件夹:

docker实战入门 docker技术入门实战_docker实战入门_10

等再加上要运行用户应用所需要的所有配置文件,二进制文件和库文件。这个文件系统在不同的Linux 发行版中是不同的。而且用户可以对这个文件进行修改。

Linux 系统在启动时,roofs 首先会被挂载为只读模式,然后在启动完成后被修改为读写模式,随后它们就可以被修改了。

再说直白点,一个容器完整的层应由三个部分组成:

  • 镜像层:也称为rootfs,提供容器启动的文件系统
  • init层: 用于修改容器中一些文件如/etc/hostname、/etc/resolv.conf等
  • 容器层:使用联合挂载统一给用户提供的可读写目录。

所以,如果不同镜像之间有相同的部分,就可以通过unionfs进行共享使用,节省空间!

不同的Linux版本,实现unionFS的技术可能不一样,使用命令docker info查看:

docker实战入门 docker技术入门实战_docker_11


我使用的是centos7.5,所以是overlay2ubuntu好像是aufs,还有些啥OverlayFS、VFS、Brtfs等就不去深入学习了。

更细节的就可以去看我另外的一篇博文了,Linux overlayFS文件系统

好了,接着来看docker image的命令

[root@localhost ~]# docker image --help

Usage:  docker image COMMAND

Manage images

Commands:
  build       Build an image from a Dockerfile
  history     Show the history of an image
  import      Import the contents from a tarball to create a filesystem image
  inspect     Display detailed information on one or more images
  load        Load an image from a tar archive or STDIN
  ls          List images
  prune       Remove unused images
  pull        Pull an image or a repository from a registry
  push        Push an image or a repository to a registry
  rm          Remove one or more images
  save        Save one or more images to a tar archive (streamed to STDOUT by default)
  tag         Create a tag TARGET_IMAGE that refers to SOURCE_IMAGE

docker image指令只有这么多了,完全可以使用--help和官方手册来学习,刚刚使用的就是ls,把经常用的都说说好了。

docker image ls

[root@localhost ~]# docker image ls --help

Usage:  docker image ls [OPTIONS] [REPOSITORY[:TAG]]

List images

Aliases:
  ls, list

Options:
  -a, --all             Show all images (default hides intermediate images)
      --digests         Show digests
  -f, --filter filter   Filter output based on conditions provided
      --format string   Pretty-print images using a Go template
      --no-trunc        Don't truncate output
  -q, --quiet           Only show image IDs

先说最常用的-q,只显示image id

[root@localhost ~]# docker image ls -q
300e315adb2f
8652b9f0cb4c
bf756fb1ae65

-a可以显示包括中间层镜像在内的所有镜像,为了加速镜像构建、重复利用资源,Docker 会利用中间层镜像。所以在使用一段时间后,可能会看到一些依赖的中间层镜像。默认的 docker image ls 列表中只会显示顶层镜像

docker image ls -a

--digests则可以显示镜像的digest

[root@localhost ~]# docker image ls -a --digests 
REPOSITORY    TAG       DIGEST                                                                    IMAGE ID       CREATED         SIZE
mysql         5.7       sha256:b3d1eff023f698cd433695c9506171f0d08a8f92a0c8063c1a4d9db9a55808df   a70d36bc331a   2 weeks ago     449MB
mysql         latest    sha256:feada149cb8ff54eade1336da7c1d080c4a1c7ed82b5e320efb5beebed85ae8c   c8562eaf9d81   2 weeks ago     546MB
centos        latest    sha256:5528e8b1b1719d34604c87e11dcd1c0a20bedf46e83b5632cdeac91b8c04efc1   300e315adb2f   8 weeks ago     209MB
centos        7         sha256:0f4ec88e21daf75124b8a9e5ca03c37a5e937e0e108a255d890492430789b60e   8652b9f0cb4c   2 months ago    204MB
hello-world   latest    sha256:31b9c7d48790f0d8c50ab433d9c3b7e17666d6993084c002c2ff1ca09b96391d   bf756fb1ae65   13 months ago   13.3kB

--filter有点学问,但是用的不太多

docker image ls --filter [dangling|before|since|lable|reference]

  • dangling: 值为true或false,true 仅返回悬虚镜像,false仅返回非悬虚镜像。
    悬虚(挂)镜像:指没有标签的镜像。悬挂镜像是一种特殊的镜像,这种镜像既没有仓库名也没有标签,他们的值都为none,除了 docker pull 可能导致这种情况, docker build 也同样可以导致这种现象。由于新旧镜像同名,旧镜像名称被取消,从而出现仓库名、标签均为none的镜像。这类无标签镜像也被称为虚悬镜像。
docker image ls -f dangling=true
  • before:需要镜像名或镜像ID作为参数,返回之前创建的全部镜像。
  • since:需要镜像名或镜像ID作为参数,返回之后创建的全部镜像。
  • lable: 根据标注的名称或值过滤。
  • reference:根据repository和tag搜索,貌似*只能搜一级空间的镜像

其实这里我们在使用仓库名搜索时,有更简单的方法,比上述好用多了。。。

  • 根据仓库名列出镜像
[root@localhost ~]# docker image ls centos
REPOSITORY   TAG       IMAGE ID       CREATED        SIZE
centos       latest    300e315adb2f   8 weeks ago    209MB
centos       7         8652b9f0cb4c   2 months ago   204MB
  • 指定仓库名和标签列出镜像
[root@localhost ~]# docker image ls centos:7
REPOSITORY   TAG       IMAGE ID       CREATED        SIZE
centos       7         8652b9f0cb4c   2 months ago   204MB

--format则是用于处理解析结果

[root@localhost ~]# docker image ls --format "table {{.ID}}\t{{.Repository}}\t{{.Tag}}" 
IMAGE ID       REPOSITORY    TAG
a70d36bc331a   mysql         5.7
c8562eaf9d81   mysql         latest
300e315adb2f   centos        latest
8652b9f0cb4c   centos        7
bf756fb1ae65   hello-world   latest

--no-trunc不打断原有结果的输出,即可以输出完全的image id

[root@localhost ~]# docker image ls --no-trunc
REPOSITORY    TAG       IMAGE ID                                                                  CREATED         SIZE
mysql         5.7       sha256:a70d36bc331a13d297f882d3d63137d24b804f29fa67158c40ad91d5050c39c5   2 weeks ago     449MB
mysql         latest    sha256:c8562eaf9d81c779cbfc318d6e01b8e6f86907f1d41233268a2ed83b2f34e748   2 weeks ago     546MB
centos        latest    sha256:300e315adb2f96afe5f0b2780b87f28ae95231fe3bdd1e16b9ba606307728f55   8 weeks ago     209MB
centos        7         sha256:8652b9f0cb4c0599575e5a003f5906876e10c1ceb2ab9fe1786712dac14a50cf   2 months ago    204MB
hello-world   latest    sha256:bf756fb1ae65adf866bd8c456593cd24beb6a0a061dedf42b26a993176745f6b   13 months ago   13.3kB

docker image tag

可以使用tag给镜像打上特定标签,方便后续工作。

[root@localhost ~]# docker image tag mysql:latest mysql:lastst1
[root@localhost ~]# docker image ls
REPOSITORY    TAG       IMAGE ID       CREATED         SIZE
mysql         5.7       a70d36bc331a   2 weeks ago     449MB
mysql         lastst1   c8562eaf9d81   2 weeks ago     546MB #这个就是多出来的,其实和lastst相同
mysql         latest    c8562eaf9d81   2 weeks ago     546MB
centos        latest    300e315adb2f   8 weeks ago     209MB
centos        7         8652b9f0cb4c   2 months ago    204MB
hello-world   latest    bf756fb1ae65   13 months ago   13.3kB

docker image inspect

inpsect就很重要了,可以看到镜像中的细节内容,比如制作者,架构,各层的数字摘要等。

[root@localhost ~]# docker image inspect centos:7
[
    {
        "Id": "sha256:8652b9f0cb4c0599575e5a003f5906876e10c1ceb2ab9fe1786712dac14a50cf",
        "RepoTags": [
            "centos:7"
        ],
        "RepoDigests": [
            "centos@sha256:0f4ec88e21daf75124b8a9e5ca03c37a5e937e0e108a255d890492430789b60e"
        ],
        "Parent": "",
        "Comment": "",
        "Created": "2020-11-14T00:20:04.644613188Z",
        "Container": "b454ba2d27117a169c53eb4c14faf363cb6aaca84df43408581fb748cc2bf796",
        "ContainerConfig": {
            "Hostname": "b454ba2d2711",
            "Domainname": "",
            "User": "",
            "AttachStdin": false,
            "AttachStdout": false,
            "AttachStderr": false,
            "Tty": false,
            "OpenStdin": false,
            "StdinOnce": false,
            "Env": [
                "PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"
            ],
            "Cmd": [
                "/bin/sh",
                "-c",
                "#(nop) ",
                "CMD [\"/bin/bash\"]"
            ],
            "Image": "sha256:05e222a9fa848efd0d4dd0969ea27c789a1eff8445d25c4f13f932ead6e3b674",
            "Volumes": null,
            "WorkingDir": "",
            "Entrypoint": null,
            "OnBuild": null,
            "Labels": {
                "org.label-schema.build-date": "20201113",
                "org.label-schema.license": "GPLv2",
                "org.label-schema.name": "CentOS Base Image",
                "org.label-schema.schema-version": "1.0",
                "org.label-schema.vendor": "CentOS",
                "org.opencontainers.image.created": "2020-11-13 00:00:00+00:00",
                "org.opencontainers.image.licenses": "GPL-2.0-only",
                "org.opencontainers.image.title": "CentOS Base Image",
                "org.opencontainers.image.vendor": "CentOS"
            }
        },
        "DockerVersion": "19.03.12",
        "Author": "",
        "Config": {
            "Hostname": "",
            "Domainname": "",
            "User": "",
            "AttachStdin": false,
            "AttachStdout": false,
            "AttachStderr": false,
            "Tty": false,
            "OpenStdin": false,
            "StdinOnce": false,
            "Env": [
                "PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"
            ],
            "Cmd": [
                "/bin/bash"
            ],
            "Image": "sha256:05e222a9fa848efd0d4dd0969ea27c789a1eff8445d25c4f13f932ead6e3b674",
            "Volumes": null,
            "WorkingDir": "",
            "Entrypoint": null,
            "OnBuild": null,
            "Labels": {
                "org.label-schema.build-date": "20201113",
                "org.label-schema.license": "GPLv2",
                "org.label-schema.name": "CentOS Base Image",
                "org.label-schema.schema-version": "1.0",
                "org.label-schema.vendor": "CentOS",
                "org.opencontainers.image.created": "2020-11-13 00:00:00+00:00",
                "org.opencontainers.image.licenses": "GPL-2.0-only",
                "org.opencontainers.image.title": "CentOS Base Image",
                "org.opencontainers.image.vendor": "CentOS"
            }
        },
        "Architecture": "amd64",
        "Os": "linux",
        "Size": 203936249,
        "VirtualSize": 203936249,
        "GraphDriver": {
            "Data": {
                "MergedDir": "/var/lib/docker/overlay2/444bd4975bb9bbbb17636326f27f2054c1d35acc29c6644758f6034876f860c2/merged",
                "UpperDir": "/var/lib/docker/overlay2/444bd4975bb9bbbb17636326f27f2054c1d35acc29c6644758f6034876f860c2/diff",
                "WorkDir": "/var/lib/docker/overlay2/444bd4975bb9bbbb17636326f27f2054c1d35acc29c6644758f6034876f860c2/work"
            },
            "Name": "overlay2"
        },
        "RootFS": {
            "Type": "layers",
            "Layers": [
                "sha256:174f5685490326fc0a1c0f5570b8663732189b327007e47ff13d2ca59673db02"
            ]
        },
        "Metadata": {
            "LastTagTime": "0001-01-01T00:00:00Z"
        }
    }
]

这里面具体的内容还是等到学dockfile后再来慢慢看吧。

docker image history

既然镜像文件由多个层组成,可以使用history子命令,该命令将列出各层的创建信息。

[root@localhost ~]# docker image history mysql:5.7
IMAGE          CREATED       CREATED BY                                      SIZE      COMMENT
a70d36bc331a   2 weeks ago   /bin/sh -c #(nop)  CMD ["mysqld"]               0B        
<missing>      2 weeks ago   /bin/sh -c #(nop)  EXPOSE 3306 33060            0B        
<missing>      2 weeks ago   /bin/sh -c #(nop)  ENTRYPOINT ["docker-entry…   0B        
<missing>      2 weeks ago   /bin/sh -c ln -s usr/local/bin/docker-entryp…   34B       
<missing>      2 weeks ago   /bin/sh -c #(nop) COPY file:a209112a748b68e0…   13.1kB    
<missing>      2 weeks ago   /bin/sh -c #(nop)  VOLUME [/var/lib/mysql]      0B        
<missing>      2 weeks ago   /bin/sh -c {   echo mysql-community-server m…   313MB     
<missing>      2 weeks ago   /bin/sh -c echo 'deb http://repo.mysql.com/a…   55B       
<missing>      2 weeks ago   /bin/sh -c #(nop)  ENV MYSQL_VERSION=5.7.33-…   0B        
<missing>      3 weeks ago   /bin/sh -c #(nop)  ENV MYSQL_MAJOR=5.7          0B        
<missing>      3 weeks ago   /bin/sh -c set -ex;  key='A4A9406876FCBD3C45…   2.61kB    
<missing>      3 weeks ago   /bin/sh -c apt-get update && apt-get install…   52.2MB    
<missing>      3 weeks ago   /bin/sh -c mkdir /docker-entrypoint-initdb.d    0B        
<missing>      3 weeks ago   /bin/sh -c set -eux;  savedAptMark="$(apt-ma…   4.17MB    
<missing>      3 weeks ago   /bin/sh -c #(nop)  ENV GOSU_VERSION=1.12        0B        
<missing>      3 weeks ago   /bin/sh -c apt-get update && apt-get install…   9.34MB    
<missing>      3 weeks ago   /bin/sh -c groupadd -r mysql && useradd -r -…   329kB     
<missing>      3 weeks ago   /bin/sh -c #(nop)  CMD ["bash"]                 0B        
<missing>      3 weeks ago   /bin/sh -c #(nop) ADD file:422aca8901ae3d869…   69.2MB

0x03 搜寻镜像

docker search

主要是讲search子命令,其实就是在hub.docker.com里面搜索的命令行界面。

[root@localhost ~]# docker search --help

Usage:  docker search [OPTIONS] TERM

Search the Docker Hub for images

Options:
  -f, --filter filter   Filter output based on conditions provided
      --format string   Pretty-print search using a Go template
      --limit int       Max number of search results (default 25)
      --no-trunc        Don't truncate output

感觉没啥讲的,-filter用的可能多点,来个例子

#搜索stars大于100以上的image
[root@localhost ~]# docker search --filter=stars=100 mysql         
NAME                 DESCRIPTION                                     STARS     OFFICIAL   AUTOMATED
mysql                MySQL is a widely used, open-source relation…   10455     [OK]       
mariadb              MariaDB is a community-developed fork of MyS…   3886      [OK]       
mysql/mysql-server   Optimized MySQL Server Docker images. Create…   767                  [OK]
percona              Percona Server is a fork of the MySQL relati…   526       [OK]

不过话说回来,这个search居然不能使用docker image search,有点奇怪。。


0x04 删除和清理镜像

docker image rm

可以使用rm来删除镜像

[root@localhost ~]# docker image rm --help

Usage:  docker image rm [OPTIONS] IMAGE [IMAGE...]

Remove one or more images

Aliases:
  rm, rmi, remove

Options:
  -f, --force      Force removal of the image
      --no-prune   Do not delete untagged parents

或者使用docker rmi命令也可以,和docker image rm等同

[root@localhost ~]# docker image rm 
centos:7            hello-world:latest  mysql:lastst1       
centos:latest       mysql:5.7           mysql:latest        
[root@localhost ~]# docker image rm mysql:lastst1 
Untagged: mysql:lastst1
# 仅仅只删除了一个tag
[root@localhost ~]# docker image rm mysql
# 不带tag时,默认删除最新的,所以mysql5.7还在
Untagged: mysql:latest
Untagged: mysql@sha256:feada149cb8ff54eade1336da7c1d080c4a1c7ed82b5e320efb5beebed85ae8c
Deleted: sha256:c8562eaf9d81c779cbfc318d6e01b8e6f86907f1d41233268a2ed83b2f34e748
Deleted: sha256:1b649b85960473808c6b812fc30c3f6a3ff1c0ffdcba5c9435daf01cf7d5373a
Deleted: sha256:19cc889447050c16c797fd209fa114ee219de23facb37c00d4137a4ed4aad922
Deleted: sha256:3c793c06a026d276cf56a6a6a75527026ed9eafa7a7d21a438f7d5ed2314148e
Deleted: sha256:1e1cd89a2bc183a7fea3dab0b543e9924278321ad0921c22cc088adbf3c2e77b
Deleted: sha256:83b2015dfd000588c7c947b2d89b3be7a8e5a3abc6ab562668c358033aa779ec
[root@localhost ~]# docker image ls
REPOSITORY    TAG       IMAGE ID       CREATED         SIZE
mysql         5.7       a70d36bc331a   2 weeks ago     449MB
centos        latest    300e315adb2f   8 weeks ago     209MB
centos        7         8652b9f0cb4c   2 months ago    204MB
hello-world   latest    bf756fb1ae65   13 months ago   13.3kB

还可以使用image id来进行删除。

[root@localhost ~]# docker image ls
REPOSITORY    TAG       IMAGE ID       CREATED         SIZE
mysql         5.7       a70d36bc331a   2 weeks ago     449MB
centos        latest    300e315adb2f   8 weeks ago     209MB
centos        7         8652b9f0cb4c   2 months ago    204MB
hello-world   latest    bf756fb1ae65   13 months ago   13.3kB
[root@localhost ~]# docker image rm  bf756fb1ae65
Untagged: hello-world:latest
Untagged: hello-world@sha256:31b9c7d48790f0d8c50ab433d9c3b7e17666d6993084c002c2ff1ca09b96391d
Deleted: sha256:bf756fb1ae65adf866bd8c456593cd24beb6a0a061dedf42b26a993176745f6b
Deleted: sha256:9c27e219663c25e0f28493790cc0b88bc973ba3b1686355f221c38a36978ac63
[root@localhost ~]# docker image ls
REPOSITORY   TAG       IMAGE ID       CREATED        SIZE
mysql        5.7       a70d36bc331a   2 weeks ago    449MB
centos       latest    300e315adb2f   8 weeks ago    209MB
centos       7         8652b9f0cb4c   2 months ago   204MB

#想删除所有镜像时可以使用docker image rm $(docker image ls -aq)

docker image prune

使用 Docker一段时间后,系统中可能会遗留一些临时的镜像文件,以及一些没有被使用的镜像,可以通过docker image prune命令来进行清理。

[root@localhost ~]# docker image prune --help

Usage:  docker image prune [OPTIONS]

Remove unused images

Options:
  -a, --all             Remove all unused images, not just dangling ones
      --filter filter   Provide filter values (e.g. 'until=<timestamp>')
  -f, --force           Do not prompt for confirmation
[root@localhost ~]# docker image prune 
WARNING! This will remove all dangling images.
Are you sure you want to continue? [y/N] y
Total reclaimed space: 0B

之间所说的悬虚镜像就可以用prune来进行清理


0x05 创建镜像

创建镜像的方法主要有三种

  • 基于已有镜像的容器创建,对应的子命令为commit
  • 基于本地模板导入,对应的子命令为import
  • 基于Dockerfile创建,对应的子命令为build

其实现在讲创建镜像感觉不太好,应该放在后面讲的,还是简单说下。

docker container commit

这命令其指的是运行容器以后,把容器再保存为一个新的镜像。但是容器命令还没学。凑合看看就行了。

#直接基于centos:7镜像创建容器并运行
[root@localhost ~]# docker run -it centos:7 /bin/bash
[root@ec5b7be704e8 /]# 

#在容器下创建文件后退出容器
[root@ec5b7be704e8 /]# echo 1 > test.txt
[root@ec5b7be704e8 /]# cat test.txt 
1
[root@ec5b7be704e8 /]# exit
exit
[root@localhost ~]# 

#查看容器
[root@localhost ~]# docker container ps -a
CONTAINER ID   IMAGE      COMMAND       CREATED         STATUS                      PORTS     NAMES
ec5b7be704e8   centos:7   "/bin/bash"   2 minutes ago   Exited (0) 52 seconds ago             reverent_hugle

#使用容器id ec5b7be704e8 进行commit镜像
[root@localhost ~]# docker container commit -a "baynk<541551992@qq.com>" -m "test_v" ec5b7be704e8 centos:test
sha256:a893853285cca5a0c97ad2e846ebf28cb1800ca19cd4c5709a53c1d9ee48ad32

#可以看到已经创建了centos:test的镜像了
[root@localhost ~]# docker image ls centos:test 
REPOSITORY   TAG       IMAGE ID       CREATED          SIZE
centos       test      a893853285cc   21 seconds ago   204MB

上述命令中的-a指的是作者信息,-m指的是commit的一些提示信息,ec5b7be704e8 为容器id,centos:testrespositorytag名。

除此之外,还有一个-c的指令,是用来执行dockfile中的命令的。

#增加了执行ls -l /test.txt的指令,创建镜像centos:test2
[root@localhost ~]# docker container commit -a "baynk<541551992@qq.com>" -m "test_v" -c 'ENTRYPOINT ["ls","-l"]' -c 'CMD ["/test.txt"]' ec5b7be704e8 centos:test2  
sha256:add1bbdbe1a00e8682087b601a6b6fcc60832d38750bd72eeeda21907711cde0

#当运行新镜像时确实已经有了命令结果了。
[root@localhost ~]# docker container run -it centos:test2    
-rw-r--r-- 1 root root 2 Feb  3 08:37 /test.txt

至于还有最后一条命令-p则是指commit镜像时暂停当时容器的运行。

[root@localhost ~]# docker container commit --help

Usage:  docker container commit [OPTIONS] CONTAINER [REPOSITORY[:TAG]]

Create a new image from a container's changes

Options:
  -a, --author string    Author (e.g., "John Hannibal Smith <hannibal@a-team.com>")
  -c, --change list      Apply Dockerfile instruction to the created image
  -m, --message string   Commit message
  -p, --pause            Pause container during commit (default true)

嗯,还有可以通过diffhistory命令查看到其中的一些改动

[root@localhost ~]# docker container diff ec5b7be704e8
C /root
A /root/.bash_history
A /test.txt

[root@localhost ~]# docker image history centos:test
IMAGE          CREATED          CREATED BY                                      SIZE      COMMENT
a893853285cc   25 minutes ago   /bin/bash                                       48B       test_v
8652b9f0cb4c   2 months ago     /bin/sh -c #(nop)  CMD ["/bin/bash"]            0B        
<missing>      2 months ago     /bin/sh -c #(nop)  LABEL org.label-schema.sc…   0B        
<missing>      2 months ago     /bin/sh -c #(nop) ADD file:b3ebbe8bd304723d4…   204MB

最后慎用 commit,因为使用docker commit意味着所有对镜像的操作都是黑箱操作,生成的镜像也被称为黑箱镜像。换句话说,就是除了制作镜像的人知道执行过什么命令、怎么生成的镜像,别人根本无从得知。而且,即使是这个制作镜像的人,过一段时间后也无法记清具体在操作的。虽然 docker diff或许可以得到一些线索,但是远远不到可以确保生成一致镜像的地步。这种黑箱镜像的维护工作是非常痛苦的。

而且,镜像所使用的分层存储,除当前层外,之前的每一层都是不会发生改变的,换句话说,任何修改的结果仅仅是在当前层进行标记、添加、修改,而不会改动上一层。如果使用 docker commit制作镜像,以及后期修改的话,每一次修改都会让镜像更加臃肿一次,所删除的上一层的东西并不会丢失,会一直如影随形的跟着这个镜像,即使根本无法访问到。这会让镜像更加臃肿。

Union FS是有最大层数限制的,比如AUFS,曾经是最大不得超过42层,现在是不得超过127层。就是commit最多127次。

docker image import

import从本地导入镜像,这个可以导入其他人打包好的镜像,也可以把镜像从仓库通过其它方式下载后,上传到本地进行导入。

书上给了个链接https://wiki.openvz.org/Download/template/precreated可以用来下OpenVZ的模板包,下好后可以直接导入

[root@localhost ~]# docker image import https://download.openvz.org/template/precreated/centos-6-x86-devel.tar.gz
Downloading from https://download.openvz.org/template/precreated/centos-6-x86-devel.tar.gz
^Cporting  3.244MB/335.4MB
[root@localhost ~]# docker image import https://download.openvz.org/template/precreated/centos-6-x86-devel.tar.gz
Downloading from https://download.openvz.org/template/precreated/centos-6-x86-devel.tar.gz
sha256:da7be36d3b6d8f14a46bd796009acc8240de65398ebea995a81af07070180bdb
[root@localhost ~]# docker image ls
REPOSITORY   TAG       IMAGE ID       CREATED         SIZE
<none>       <none>    da7be36d3b6d   4 minutes ago   828MB
centos       test2     add1bbdbe1a0   3 hours ago     204MB
centos       test      a893853285cc   4 hours ago     204MB
mysql        5.7       a70d36bc331a   2 weeks ago     449MB
centos       latest    300e315adb2f   8 weeks ago     209MB
centos       7         8652b9f0cb4c   2 months ago    204MB

直接通过链接下来后,导入了,但是没有进行命名,改个名就好了。

[root@localhost ~]# docker image tag da7be36d3b6d centos:6 
[root@localhost ~]# docker image ls
REPOSITORY   TAG       IMAGE ID       CREATED         SIZE
centos       6         da7be36d3b6d   6 minutes ago   828MB

docker image build

通过dockerfile创建镜像就是主要的方式了,后面有一章来讲这个,简单说明下。

#先创建一个工作目录
[root@localhost ~]# mkdir build-test
[root@localhost ~]# cd build-test/

#创建Dockerfile文件,在文件中写入内容。
[root@localhost build-test]# vim Dockerfile
FROM nginx
RUN echo '这是本地构建的nginx镜像' > /usr/share/nginx/html/index.html

#通过docker build进行创建镜像
[root@localhost build-test]# docker image build -t nginx:test .
Sending build context to Docker daemon  2.048kB
Step 1/2 : FROM nginx
latest: Pulling from library/nginx
a076a628af6f: Already exists 
0732ab25fa22: Pull complete 
d7f36f6fe38f: Pull complete 
f72584a26f32: Pull complete 
7125e4df9063: Pull complete 
Digest: sha256:10b8cc432d56da8b61b070f4c7d2543a9ed17c2b23010b43af434fd40e2ca4aa
Status: Downloaded newer image for nginx:latest
 ---> f6d0b4767a6c
Step 2/2 : RUN echo '这是本地构建的nginx镜像' > /usr/share/nginx/html/index.html
 ---> Running in bf0a94b09139
Removing intermediate container bf0a94b09139
 ---> 57196ada9b95
Successfully built 57196ada9b95
Successfully tagged nginx:test
[root@localhost build-test]# docker image ls
REPOSITORY   TAG       IMAGE ID       CREATED          SIZE
nginx        test      57196ada9b95   28 seconds ago   133MB

可以看到已经成功创建镜像,注意命令docker image build -t nginx:test .最后是有一个.符号的,详细的后面再说。


0x06 存出和载入镜像

docker image save

如果要导出镜像到本地文件就可以使用此命令。

[root@localhost ~]# docker image save nginx:test > nginx-test.tar
或者
[root@localhost ~]# docker image save -o nginx-test2.tar nginx:test 
上面两条命令都可以存出镜像
[root@localhost ~]# ls
anaconda-ks.cfg  build-test  index.html  nginx-test2.tar  nginx-test.tar  test

docker image load

使用load可以载入存出的镜像

#先删除存在的镜像
[root@localhost ~]# docker image rm nginx:test
Untagged: nginx:test
Deleted: sha256:57196ada9b95d26c4caa3792f5dbb2abbf75c5e01c336f6ade7d35a07ba6f20f
Deleted: sha256:b6c9a3aece8cae8ff5f17f1ccd05d9edd9fb66dd35ec40e4c4118c639cd5a202
[root@localhost ~]# docker image ls nginx:test
REPOSITORY   TAG       IMAGE ID   CREATED   SIZE

#载入之间的tar文件
[root@localhost ~]# docker image load -i nginx-test.tar 
462dd97ec6b9: Loading layer  4.096kB/4.096kB
Loaded image: nginx:test
[root@localhost ~]# docker image ls nginx:test          
REPOSITORY   TAG       IMAGE ID       CREATED          SIZE
nginx        test      57196ada9b95   16 minutes ago   133MB

0x07 上传镜像

docker image pull

主要说的是将镜像pull到远程仓库去,可以传到官方,也可以传到私人仓库。

这里以官方hub为例,先去官网注册账号。注册后,在命令行中先登陆。

[root@localhost ~]# 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: baynk
Password: 
WARNING! Your password will be stored unencrypted in /root/.docker/config.json.
Configure a credential helper to remove this warning. See
https://docs.docker.com/engine/reference/commandline/login/#credentials-store

Login Succeeded

接下来在push之前用tag改下名字,在前面加下baynk,这个是我hub的名字,不然上传镜像会出现权限错误

[root@localhost ~]# docker image tag nginx:test baynk/nginx:test
[root@localhost ~]# docker image push baynk/nginx:test 
The push refers to repository [docker.io/baynk/nginx]
462dd97ec6b9: Pushed 
85fcec7ef3ef: Mounted from library/nginx 
3e5288f7a70f: Mounted from library/nginx 
56bc37de0858: Mounted from library/nginx 
1c91bf69a08b: Mounted from library/nginx 
cb42413394c4: Mounted from library/httpd 
test: digest: sha256:5e842b6818f6faaea8e7d111df41b972012bd166af5784a821742fe3f408ee2a size: 1569

已经上传成功,接下来,删除本地镜像,再从hub上拉取尝试。

[root@localhost ~]#  docker image rm baynk/nginx:test 
Untagged: baynk/nginx:test
Untagged: baynk/nginx@sha256:5e842b6818f6faaea8e7d111df41b972012bd166af5784a821742fe3f408ee2a
[root@localhost ~]#  docker image pull baynk/nginx:test   
test: Pulling from baynk/nginx
Digest: sha256:5e842b6818f6faaea8e7d111df41b972012bd166af5784a821742fe3f408ee2a
Status: Downloaded newer image for baynk/nginx:test
docker.io/baynk/nginx:test
[root@localhost ~]# docker image ls baynk/nginx:test 
REPOSITORY    TAG       IMAGE ID       CREATED          SIZE
baynk/nginx   test      57196ada9b95   41 minutes ago   133MB

同时在hub上也可以看到上传成功的镜像

docker实战入门 docker技术入门实战_docker实战入门_12