Docker学习笔记之容器的操作(1)
概述
在这一篇中,我们重点学习create、start、stop等命令的操作;在这过程中,也会使用到上一篇 Docker学习笔记之 Docker学习笔记之使用镜像 的一些命令,且当是复习吧。
1、新建容器
我们可以使用 create 命令新建容器,格式为:docker [container] create [OPTIONS] NAME[:TAG],下面我们来创建一个ubuntu:21.10的容器器,示例如下:
[root@localhost ~]# docker create -it ubuntu:21.10
Unable to find image 'ubuntu:21.10' locally
21.10: Pulling from library/ubuntu
34031c10e7d2: Pull complete
Digest: sha256:ac47e1cbf1a83c9eec71890a9d4e5ad35c7ffe3c8ab62ca427e63f0899a6c872
Status: Downloaded newer image for ubuntu:21.10
d46552e430bb773078fb70a86c5bc5137cdc1fb0020856c6d3f3ec08b141f41f
上面是上面用到了两个参数(除了这两个,还有很多其他的参数,这里不一一介绍):
-i:保持标准输入打开;
-t:是否分配一个伪终端;
要注意的是,上面的操作,其实docker帮我们做了两件事情:
(1)查询本地是否存在指定版本的镜像,如果不存在,则从Docker Hub 下载指定版本的镜像;
(2)基于本地指定版本的镜像,使用指定的参数/命令新建容器,从上面看到的 d46552e430bb.... 这样的字符串,实例上是容器新建成功后,输入了容器的ID;
使用create命令新建的容器,并不会自动运行,我们可以用 start 命令 将我们刚才新建的容器运行起来,格式如下:docker [container] start CONTAINERID,示例如下:
[root@localhost ~]# docker start d46552e430bb
d46552e430bb
[root@localhost ~]# docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
d46552e430bb ubuntu:21.10 "bash" 17 minutes ago Up 13 seconds angry_pascal
到了这里,细心的同学,可能会想,是不是 我们上一篇文章中学习的 run 命令( docker run -it ubuntu:21.10 bash )等价于 create + start 命令呢( docker create -it ubuntu:21.10 && docker start d46552e430bb )?答案是肯定的。
2、查看日志
在这上面的操作中,都是最基本的一些容器操作,但如果我们运行的是比较复杂的容器,我们需要了解容器的运行情况,当是 用 ps 查看,是远远不够的,那么这个时候,我们可以用 logs 命令,进一步了解容器的运行情况,格式为:docker [container] logs CONTAINERID 。在我们执行logs命令之前,我们回看上面运行的 容器 d46552e430bb ,它是没有进行任何操作的,因此我们需要先使用 docker attach CONTAINERID 进入这个容器进行一些操作后,然后再使用 logs 命令查看日志,这样理解起来才会比较直观,示例如下:
[root@localhost ~]# docker attach d46552e430bb
root@d46552e430bb:/# echo "hello cnblogs"
hello cnblogs
root@d46552e430bb:/# pwd
/
root@d46552e430bb:/# ps
PID TTY TIME CMD
1 pts/0 00:00:00 bash
9 pts/0 00:00:00 ps
root@d46552e430bb:/# exit
exit
[root@localhost ~]# docker container logs d46552e430bb
root@d46552e430bb:/# echo "hello cnblogs"
hello cnblogs
root@d46552e430bb:/# pwd
/
root@d46552e430bb:/# ps
PID TTY TIME CMD
1 pts/0 00:00:00 bash
9 pts/0 00:00:00 ps
root@d46552e430bb:/# exit
exit
从上图可以看到,使用 logs 命令后可以看到容器的运行日志信息;
3、停止容器
接下来,我们来了解一下停止容器的相关命令。
- 暂停容器,使用命令 docker [container] pause CONTAINER [CONTAINER..] 来暂停一个或多个运行中的容器。示例如下:
从上图可以看到,执行 pause 前后,容器的状态是不一样的,对于暂停的容器,我们还可以使用 docker [container] unpause CONTAINER [CONTAINER..] 命令来恢复到运行状态。
- 终止容器,使用命令 docker [container] stop [-t|--time[=10]] [CONTAINER..] 可以终止一个或多个运行中的容器。这个命令首先会向容器发送一个SIGTERM信号,等待一段超时时间后(默认是10秒),再发送SIGKILL信号终止容器的运行状态。示例如下:
[root@localhost ~]# docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
6443da401f83 f5cbed4244ba "bash" 32 hours ago Up 32 hours nostalgic_rosalind
9b7a9a6d8b7a dotnet-core "dotnet MyTest.Docke…" 7 days ago Up 47 hours 5000/tcp, 0.0.0.0:5000->5061/tcp, :::5000->5061/tcp hello-baby
45499d54d1dd dotnet-core "dotnet MyTest.Docke…" 7 days ago Up 47 hours 5000/tcp, 0.0.0.0:5010->5061/tcp, :::5010->5061/tcp hello-boy
[root@localhost ~]# docker stop 6443da401f83
6443da401f83
[root@localhost ~]# docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
9b7a9a6d8b7a dotnet-core "dotnet MyTest.Docke…" 7 days ago Up 47 hours 5000/tcp, 0.0.0.0:5000->5061/tcp, :::5000->5061/tcp hello-baby
45499d54d1dd dotnet-core "dotnet MyTest.Docke…" 7 days ago Up 47 hours 5000/tcp, 0.0.0.0:5010->5061/tcp, :::5010->5061/tcp hello-boy
从上图可以看到停止运行后的容器,不会在当前运行容器列表中显示出来,我们可以用 docker ps -a 显示所的的容器,包括各种状态的容器所有。
为了有助于各位同学理解容器各状态之间的变换,我们可以看下面的容器的生命周期:
4、进入容器
在有些时候,我们在创建容器的时候,可能使用了-d参数,容器运行的时候,会自动进入后台运行,用户无法看到容器中的信息,也无法进行操作,那么这个时候,我们可以使用命令 attach 或 exec 命令 进入容器进行操作。
- atach命令
在上面的介绍 查看日志 的时候,就使用到了这个命令,这里详细给大家介绍一下,其格式为:docker [container] attach [--detach-keys=[=[]]] [--no-stdin] [--sig-proxy[=true]] CONTAINER 。
--detach-keys=[=[]]:指定退出attach模式的快捷键序列,默认为CTRL-p、CTRL-q;
--no-stdin=true|false:是否关闭标准输入,默认为保持打开;
--sig-proxy=true|false:是否代理收到的系统信号给应用进程,默认为true;
示例如下(这里重复上面查看日志的部分命令):
[root@localhost ~]# docker attach d46552e430bb
root@d46552e430bb:/# echo "hello cnblogs"
hello cnblogs
root@d46552e430bb:/# pwd
/
root@d46552e430bb:/# ps
PID TTY TIME CMD
1 pts/0 00:00:00 bash
9 pts/0 00:00:00 ps
root@d46552e430bb:/# exit
- exec命令
从Docker 1.3.0版本起,Docker提供了一个更加方便的 exec 命令,可以在运行的容器中直接执行任意命令。
它的格式为:docker [container] exec [-d|--detach] [--detach-keys[=[]]] [-i|--interactive] [--privileged] [-t|--tty] [-u|--user[=USER]] CONTAINER [ARG...] 。
常的参数有:
-d, --detach:在容器的后台执行命令;
--detach-keys="":指定将容器切回后台的按键;
-e, --env=[]:指定环境变量列表;
-i, --interactive=true|false:打开标准输入接受用户输入命令,默认值为false;
--privileged=true|false:是否给执行命令以高权限,默认值为false;
-t, --tty=true|false:分配伪终端,默认值为false;
-u, --user="":执行命令的用户名或ID;
例如,我们进入前面创建的容器中,并启动一个 bash:
[root@localhost ~]# docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
d46552e430bb ubuntu:21.10 "bash" 3 hours ago Up 59 seconds angry_pascal
9b7a9a6d8b7a dotnet-core "dotnet MyTest.Docke…" 7 days ago Up About a minute 5000/tcp, 0.0.0.0:5000->5061/tcp, :::5000->5061/tcp hello-baby
45499d54d1dd dotnet-core "dotnet MyTest.Docke…" 7 days ago Up About a minute 5000/tcp, 0.0.0.0:5010->5061/tcp, :::5010->5061/tcp hello-boy
[root@localhost ~]# docker exec -it d46552e430bb /bin/bash
root@d46552e430bb:/# echo "Hello world!"
Hello world!
root@d46552e430bb:/# ps
PID TTY TIME CMD
17 pts/1 00:00:00 bash
25 pts/1 00:00:00 ps
root@d46552e430bb:/# ls
bin boot dev etc home lib lib32 lib64 libx32 media mnt opt proc root run sbin srv sys tmp usr var
root@d46552e430bb:/#
到了这里,我们看到的 attach 和 exec 都可以实现进入终端执行命令 的功能,那他们有区别吗?答案是有区别:使用attach 命令进入容器执行的命令,会影响到其他同样使用attach命令进入容器的其他用户的输出,简单来说,AB用户都使用attach命令进入容器并对容器执行命令,那么AB看到的东西,将会是一样的,即使未操作的一方也会同步操作一方的信息;而使用 exec 命令进入容器执行的相关操作,并不会影响容器内的其他应用。
由于内容较多,我们将在下一篇 Docker学习笔记之容器的操作II 中继续学习。