本文读者主要针对运维工程师及后端开发人员,旨在通过该文章,让大家对docker有整体的认识,并且能够掌握常用的操作命令,同时也算是作者这2周使用Docker的一些经验总结吧。
在介绍常用命令前,我们首先要建立对docker的整体认识。
Docker 可以让开发者打包他们的应用以及依赖包到一个轻量级、可移植的容器中,然后发布到任何流行的 Linux 机器上,也可以实现虚拟化。容器是完全使用沙箱机制,相互之间不会有任何接口,更重要的是容器性能开销极低。
Docker 是一个用于开发,交付和运行应用程序的开放平台。Docker 使您能够将应用程序与基础架构分开,从而可以快速交付软件。借助 Docker,您可以与管理应用程序相同的方式来管理基础架构。通过利用 Docker 的方法来快速交付,测试和部署代码,您可以大大减少编写代码和在生产环境中运行代码之间的延迟。
3个基本概念
镜像(Image):Docker 镜像(Image),就相当于是一个 root 文件系统。比如官方镜像 ubuntu:16.04 就包含了完整的一套 Ubuntu16.04 最小系统的 root 文件系统。
容器(Container):镜像(Image)和容器(Container)的关系,就像是面向对象程序设计中的类和实例一样,镜像是静态的定义,容器是镜像运行时的实体。容器可以被创建、启动、停止、删除、暂停等。
仓库(Repository):仓库可看成一个代码控制中心,用来保存镜像。
架构模式
Docker 使用客户端-服务器 (C/S) 架构模式,使用远程API来管理和创建Docker容器。
Docker 容器通过 Docker 镜像来创建。
容器与镜像的关系类似于面向对象编程中的对象与类。
这里介绍基本流程和命令,参数细节,可见后面的章节。
编译镜像的过程中,可能也会涉及到一些公共的基础镜像的拉取,这里先提一下。
一般在开发初期,对于同一版本的docker可能会多次build测试,这个时候需要停止原来的docker,编译新的docker然后运行。
列出本地主机上的镜像
$ docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
text_classify_gpu v2.0 a46a8bd60eba 1 days ago 5.32GB
text_classify_gpu v1.0 a46a8bd60eba 8 days ago 5.31GB
nvidia/cuda 10.0-cudnn7-devel-centos7 7fc1453d6e94 4 months ago 3.35GB
以上信息中,各项内容详情如下:
REPOSITORY
:表示镜像的仓库源TAG
:镜像的标签IMAGE ID
:镜像IDCREATED
:镜像创建时间SIZE
:镜像大小有2种方式,一般使用第二种比较多:
docker search
命令来搜索镜像$ docker search nvidia
NAME DESCRIPTION STARS OFFICIAL AUTOMATED
nvidia/cuda CUDA and cuDNN images from gitlab.com/nvidia… 830
nvidia/digits DEPRECATED 72
nvidia/opengl OpenGL images with libglvnd from Nvidia 28
nvidia/cudagl CUDA + OpenGL images from gitlab.com/nvidia/… 27
nvidia/k8s-device-plugin Images for github.com/NVIDIA/k8s-device-plug… 24
nvidia/cuda-ppc64le CUDA and cuDNN images from gitlab.com/nvidi… 17
nvidia/opencl OpenCL images from gitlab.com/nvidia/opencl 16
nvidia/driver Driver images from https://gitlab.com/nvidia… 16
willprice/nvidia-ffmpeg NVIDIA Hardware Accelerated FFmpeg build 13
以上信息中,各项内容详情如下:
NAME
: 镜像仓库源的名称DESCRIPTION
: 镜像的描述OFFICIAL
: 是否 docker 官方发布stars
: 类似 Github 里面的 star,表示点赞、喜欢的意思。AUTOMATED
: 自动构建。从Docker源拉取最新的镜像进行安装
$ docker pull text_classify_gpu
Using default tag: latest
实际情况下,我们往往不需要最新的版本,而是指定版本,这个时候可以登录Docker Hub网站,找到对应的Tag进行安装。
$ docker pull text_classify_gpu:v1.0
使用命令docker build
,来创建一个新的镜像。
为此,我们需要创建一个 Dockerfile 文件,其中包含一组指令来告诉 Docker 如何构建我们的镜像。
下面以Python工程为例,写一个Dockerfile的示例:
FROM python:3.7
MAINTAINER xiaoi
# 开放端口
EXPOSE 5000
# 设置环境变量
ENV pypi https://pypi.douban.com/simple
ENV DIR /mnt/PseudoRegular
# 切换工作目录
COPY ./ ${DIR}
WORKDIR ${DIR}
RUN pip install --no-cache-dir -r requirements.txt flask uwsgi -i ${pypi}
CMD ["sh","app.sh"]
每一个指令都会在镜像上创建一个新的层,每一个指令的前缀都必须是大写的。
第一条FROM,指定使用哪个镜像源
RUN 指令告诉docker 在镜像内执行命令,安装了什么。
然后,我们使用 Dockerfile 文件,通过 docker build 命令来构建一个镜像。
对于Dockerfile的编写可以看:《一篇文章教会你dockerfile的编写和使用》。
$ docker build -t pseudo-regular:v1.0 .
Sending build context to Docker daemon 153.6kB
Step 1/9 : FROM python:3.7
---> af86b73e120c
Step 2/9 : MAINTAINER xiaoi
---> Running in be3eeaeb3165
Removing intermediate container be3eeaeb3165
---> 35675d4a4708
......
Successfully built e4c6e1801984
Successfully tagged pseudo-regular:v1.0
参数说明:
-t
:指定要创建的目标镜像名.
:Dockerfile 文件所在目录,可以指定Dockerfile的绝对路径查看镜像列表:
docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
pseudo-regular v1.0 e4c6e1801984 6 minutes ago 1.03GB
python 3.7 af86b73e120c 9 days ago 903MB
gzxiaoi/text_classify_gpu v2.0 a46a8bd60eba 9 days ago 5.31GB
nvidia/cuda 10.0-cudnn7-devel-centos7 7fc1453d6e94 4 months ago 3.35GB
接下来就可以使用新的镜像来创建容器了,在后面的章节会有详细介绍。
更新镜像之前,我们需要使用镜像来创建一个容器。
$ docker run -t -i text_classify_gpu:v1.0 /bin/bash
root@e218edb10161:/#
在运行的容器内使用apt-get update
命令进行更新,或者对内部的内容进行修改。
在完成操作之后,输入 exit 命令来退出这个容器。
此时 ID 为 e218edb10161 的容器,是按我们的需求更改的容器。我们可以通过命令docker commit
来提交容器副本。
$ docker commit -m="has update" -a="jason" e218edb10161 text_classify_gpu:v2.0
sha256:70bf1840fd7c0d2d8ef0a42a817eb29f854c1af8f7c59fc03ac7bdee9545aff8
各个参数说明:
-m
: 提交的描述信息-a
: 指定镜像作者e218edb10161
:容器 IDtext_classify_gpu:v2.0
: 指定要创建的目标镜像名接下来我们查看镜像列表
$ docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
text_classify_gpu v2.0 70bf1840fd7c 1 days ago 5.32GB
text_classify_gpu v1.0 a46a8bd60eba 8 days ago 5.31GB
nvidia/cuda 10.0-cudnn7-devel-centos7 7fc1453d6e94 4 months ago 3.35GB
$ docker rmi a46a8bd60eba
删除后查看进行列表
$ docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
text_classify_gpu v2.0 70bf1840fd7c 1 days ago 5.32GB
nvidia/cuda 10.0-cudnn7-devel-centos7 7fc1453d6e94 4 months ago 3.35GB
查看运行中的容器列表
$ docker ps
查看所有的容器列表
$ docker ps -a
$ docker run -it -p 10000:5000 --name=pseudo-new pseudo-regular:v1.0 /bin/bash
参数说明:
-i
: 交互式操作。-t
: 终端。-p
: 将docker中5000端口映射到宿主机的10000端口--name
: 容器名字。pseudo-regular:v1.0
: 依赖的镜像名及对应的Tag/bin/bash
:放在镜像名后的是命令,这里我们希望有个交互式 Shell,因此用的是 /bin/bash。exit
: 实际一般会启动容器在后台运行-d
,设置Docker重启时容器自动启动--restart=always
,命令如下:
$ docker run -d -p 10000:5000 --restart=always --name=pseudo-new pseudo-regular:v1.0
查看运行中的容器
$ docker ps -a
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
19885aecf783 pseudo-regular:v1.0 "sh app.sh" 5 seconds ago Up 4 seconds 0.0.0.0:10000->5000/tcp pseudo-new
使用命令停止容器,参数为容器ID/容器名
$ docker stop pseudo-new
pseudo-new
首先使用docker ps -a
命令查看容器列表,根据指定的容器ID,启动命令如下:
$ docker ps -a
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
b750bbbcfd88 pseudo-regular:v1.0 "sh app.sh" About a minute ago Exited (137) 40 seconds ago pseudo-new
$ docker start b750bbbcfd88
19885aecf783
接下来查看运行中的容器列表:
$ docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
19885aecf783 pseudo-regular:v1.0 "sh app.sh" 2 minutes ago Up 3 seconds 0.0.0.0:10000->5000/tcp pseudo-new
可以使用docker restart
命令,参数为容器ID/容器名
$ docker restart pseudo-new
pseudo-new
$ docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
19885aecf783 pseudo-regular:v1.0 "sh app.sh" 9 minutes ago Up 6 seconds 0.0.0.0:10000->5000/tcp pseudo-new
$ docker restart 19885aecf783
19885aecf783
$ docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
19885aecf783 pseudo-regular:v1.0 "sh app.sh" 10 minutes ago Up 6 seconds 0.0.0.0:10000->5000/tcp pseudo-new
在使用 -d 参数时,容器启动后会进入后台。
此时想要进入容器,可以通过以下2个指令进入:
docker attach
: 退出容器终端后容器也会停止运行docker exec
: 退出容器终端,不会导致容器的停止(推荐使用)attach 命令
$ docker attach 19885aecf783
exec 命令
$ docker exec -it 19885aecf783 /bin/bash
如果要导出本地某个容器,可以使用docker export
命令。
$ docker export 19885aecf783 > pseudo-new.tar
可以使用docker import
从容器快照文件中再导入为镜像,以下实例将快照文件 pseudo-new.tar 导入到镜像 test/pseudo-new:v1.1:
$ cat docker/pseudo-new.tar | docker import - test/pseudo-new:v1.1
删除容器使用docker rm
命令
docker rm -f 19885aecf783
参数说明:
-f
: 通过 SIGKILL 信号强制删除一个运行中的容器,等效docker stop + docker rm
顺便说一下,删除所有已经停止的容器命令
$ docker rm $(docker ps -a -q)
docker logs [OPTIONS] CONTAINER
OPTIONS说明:
-f
: 跟踪日志输出--since
:显示某个开始时间的所有日志-t
: 显示时间戳--tail
:仅列出最新N条容器日志$ docker system df -v
Images space usage:
REPOSITORY TAG IMAGE ID CREATED SIZE SHARED SIZE UNIQUE SIZE CONTAINERS
pseudo-regular v1.0 e4c6e1801984 4 hours ago 1.027GB 903.1MB 123.9MB 1
python 3.7 af86b73e120c 9 days ago 903.1MB 903.1MB 0B 0
text_classify_gpu v2.0 a46a8bd60eba 10 days ago 5.31GB 3.351GB 1.959GB 0
nvidia/cuda 10.0-cudnn7-devel-centos7 7fc1453d6e94 4 months ago 3.351GB 3.351GB 0B 0
Containers space usage:
CONTAINER ID IMAGE COMMAND LOCAL VOLUMES SIZE CREATED STATUS NAMES
786ecd7d293e pseudo-regular:v1.0 "sh app.sh" 0 154kB 18 minutes ago Up 18 minutes pseudo-new
Local Volumes space usage:
VOLUME NAME LINKS SIZE
Build cache usage: 0B
CACHE ID CACHE TYPE SIZE CREATED LAST USED USAGE SHARED
$ docker system df
TYPE TOTAL ACTIVE SIZE RECLAIMABLE
Images 4 1 6.337GB 6.213GB (98%)
Containers 1 1 153.8kB 0B (0%)
Local Volumes 0 0 0B 0B
Build Cache 0 0 0B 0B
其他相关资料:
CentOS docker 安装:https://www.runoob.com/docker/centos-docker-install.html
docker 命令大全:https://www.runoob.com/docker/docker-command-manual.html