Docker 学习日志 (二)
8 容器内部都在干些什么现在我们已经有了一个在后台运行 while 循环的守护型容器。为了探究该容器内部都在干些什么,可以用 dockerlogs 命令来获取容器的日志,如代码清单3-19所示。代码清单3-19 获取守护式容器的日志$ sudo docker logs daemon_davehello worldhello worldhello worldhell
8 容器内部都在干些什么
现在我们已经有了一个在后台运行 while
循环的守护型容器。为了探究该容器内部都在干些什么,可以用 docker logs
命令来获取容器的日志,如代码清单3-19所示。
代码清单3-19 获取守护式容器的日志
$ sudo docker logs daemon_dave
hello world
hello world
hello world
hello world
hello world
hello world
hello world
. . .
这里,我们可以看到 while
循环正在向日志里打印 hello world
。Docker会输出最后几条日志项并返回。我们也可以在命令后使用 -f
参数来监控Docker的日志,这与 tail -f
命令非常相似,如代码清单3-20所示。
代码清单3-20 跟踪守护式容器的日志
$ sudo docker logs -f daemon_dave
hello world
hello world
hello world
hello world
hello world
hello world
hello world
. . .
提示
可以通过Ctr+C退出日志跟踪。
我们也可以跟踪容器日志的某一片段,和之前类似,只需要在 tail
命令后加入 -f --tail
标志即可。例如,可以用 docker logs --tail 10 daemon_dave
获取日志的最后10行内容。另外,也可以用 docker logs --tail 0 -f daemon_dave
命令来跟踪某个容器的最新日志而不必读取整个日志文件。
为了让调试更简单,还可以使用 -t
标志为每条日志项加上时间戳,如代码清单3-21所示。
代码清单3-21 跟踪守护式容器的最新日志
$ sudo docker logs -ft daemon_dave
[May 10 13:06:17.934] hello world
[May 10 13:06:18.935] hello world
[May 10 13:06:19.937] hello world
[May 10 13:06:20.939] hello world
[May 10 13:06:21.942] hello world
. . .
提示
同样,可以通过Ctr+C退出日志跟踪。
9 Docker日志驱动
自Docker 1.6开始,也可以控制Docker守护进程和容器所用的日志驱动,这可以通过--log-driver选项来实现。可以在启动Docker守护进程或者执行docker run命令时使用这个选项。
有好几个选项,包括默认的json-file,json-file也为我们前面看到的docker logs命令提供了基础。
其他可用的选项还包括syslog,该选项将禁用docker logs命令,并且将所有容器的日志输出都重定向到Syslog。可以在启动Docker守护进程时指定该选项,将所有容器的日志都输出到Syslog,或者通过docker run对个别的容器进行日志重定向输出。
代码清单3-22 在容器级别启动Syslog
$ sudo docker run --log-driver="syslog" --name daemon_dwayne -d
ubuntu /bin/sh -c "while true; do echo hello world; sleep 1;
done"
. . .
提示
如果是在Docker Toolbox中运行Docker,应该在虚拟机中启动Syslog守护进程。可以先通过docker-machine ssh命令连接到Docker Toolbox虚拟机,再在其中运行syslogd命令来启动Syslog守护进程。
上面的命令会将daemon_dwayne容器的日志都输出到Syslog,导致docker logs命令不输出任何东西。
最后,还有一个可用的选项是none,这个选项将会禁用所有容器中的日志,导致docker logs命令也被禁用。
提示
新的日志驱动也在不断地增加,在Docker 1.8中,新增了对Graylog GELF协议、Fluentd以及日志轮转驱动的支持。
10 查看容器内的进程
除了容器的日志,也可以查看容器内部运行的进程。要做到这一点,要使用docker top
命令,如代码清单3-23所示。
代码清单3-23 查看守护式容器的进程
$ sudo docker top daemon_dave
该命令执行后,可以看到容器内的所有进程(主要还是我们的 while
循环)、运行进程的用户及进程ID,如代码清单3-24所示。
代码清单3-24 docker
** top
命令的输出结果
PID USER COMMAND
977 root /bin/sh -c while true; do echo hello world; sleep 1;
done
1123 root sleep 1
11 Docker统计信息
除了 docker top
命令,还可以使用 docker stats
命令,它用来显示一个或多个容器的统计信息。让我们来看看它的输出是什么样的。下面我们来查看一下容器daemon_dave
以及其他守护式容器的统计信息。
代码清单3-25 docker stats命令
$ sudo docker stats daemon_dave daemon_kate daemon_clare daemon_sarah
CONTAINER CPU % MEM USAGE/LIMIT MEM % NET I/O BLOCK I/O
daemon_clare 0.10% 220 KiB/994 MiB 0.02% 1.898 KiB/648 B 12.75 MB / 0 B
daemon_dave 0.14% 212 KiB/994 MiB 0.02% 5.062 KiB/648 B 1.69 MB / 0 B
daemon_kate 0.11% 216 KiB/994 MiB 0.02% 1.402 KiB/648 B 24.43 MB / 0 B
daemon_sarah 0.12% 208 KiB/994 MiB 0.02% 718 B/648 B 11.12 MB / 0 B
我们能看到一个守护式容器的列表,以及它们的CPU、内存、网络I/O及存储I/O的性能和指标。这对快速监控一台主机上的一组容器非常有用。
注意
docker stats是Docker 1.5.0中引入的命令。
12 在容器内部运行进程
在Docker 1.3之后,也可以通过 docker exec
命令在容器内部额外启动新进程。可以在容器内运行的进程有两种类型:后台任务和交互式任务。后台任务在容器内运行且没有交互需求,而交互式任务则保持在前台运行。对于需要在容器内部打开shell的任务,交互式任务是很实用的。下面先来看一个后台任务的例子,如代码清单3-26所示。
代码清单3-26 在容器中运行后台任务
$ sudo docker exec -d daemon_dave touch /etc/new_config_file
这里的 -d
标志表明需要运行一个后台进程, -d
标志之后,指定的是要在内部执行这个命令的容器的名字以及要执行的命令。上面例子中的命令会在 daemon_dave
容器内创建了一个空文件,文件名为 /etc/new_config_file
。通过 docker exec
后台命令,可以在正在运行的容器中进行维护、监控及管理任务。
提示
从Docker 1.7开始,可以对docker exec启动的进程使用–u标志为新启动的进程指定一个用户属主。
我们也可以在 daemon_dave
容器中启动一个诸如打开shell的交互式任务,如代码清单3-27所示。
代码清单3-27 在容器内运行交互命令
$ sudo docker exec -t -i daemon_dave /bin/bash
和运行交互容器时一样,这里的 -t
和 -i
标志为我们执行的进程创建了TTY并捕捉 STDIN
。接着我们指定了要在内部执行这个命令的容器的名字以及要执行的命令。在上面的例子中,这条命令会在 daemon_dave
容器内创建一个新的bash会话,有了这个会话,我们就可以在该容器中运行其他命令了。
注意
docker exec命令是Docker 1.3引入的,早期版本并不支持该命令。对于早期Docker版本,请参考第6章中介绍的nsenter命令。
13 停止守护式容器
要停止守护式容器,只需要执行 docker stop
命令,如代码清单3-28所示。
代码清单3-28 停止正在运行的Docker容器
$ sudo docker stop daemon_dave
当然,也可以用容器ID来指代容器名称,如代码清单3-29所示。
代码清单3-29 通过容器ID停止正在运行的容器
$ sudo docker stop c2c4e57c12c4
注意
docker stop命令会向Docker容器进程发送SIGTERM信号。如果想快速停止某个容器,也可以使用docker kill命令来向容器进程发送SIGKILL信号。
要想查看已经停止的容器的状态,则可以使用 docker ps
命令。还有一个很实用的命令 docker ps -n x
,该命令会显示最后 x
个容器,不论这些容器正在运行还是已经停止。
14 自动重启容器
如果由于某种错误而导致容器停止运行,还可以通过 --restart
标志,让Docker自动重新启动该容器。 --restart
标志会检查容器的退出代码,并据此来决定是否要重启容器。默认的行为是Docker不会重启容器。
代码清单3-30是一个在 docker run
命令中使用 —restart
标志 的例子。
代码清单3-30 自动重启容器
$ sudo docker run --restart=always --name daemon_dave -d ubuntu /
bin/sh -c "while true; do echo hello world; sleep 1; done"
在本例中, --restart
标志被设置为 always
。无论容器的退出代码是什么,Docker都会自动重启该容器。除了 always
,还可以将这个标志设为 on-failure
,这样,只有当容器的退出代码为非0值的时候,才会自动重启。另外, on-failure``还接受一个可选的
重启次数参数,如代码清单3-31所示。
代码清单3-31 为 on-failure
指定 count
参数
--restart=on-failure:5
这样,当容器退出代码为非0时,Docker会尝试自动重启该容器,最多重启5次。
注意
--restart标志是Docker1.2.0引入的选项。
15 深入容器
除了通过 docker ps
命令获取容器的信息,还可以使用 docker inspect``来
获得更多的容器信息,如代码清单3-32所示。
代码清单3-32 查看容器
$ sudo docker inspect daemon_dave
[{
"ID": "
c2c4e57c12c4c142271c031333823af95d64b20b5d607970c334784430bcbd0f
",
"Created": "2014-05-10T11:49:01.902029966Z",
"Path": "/bin/sh",
"Args": [
"-c",
"while true; do echo hello world; sleep 1; done"
],
"Config": {
"Hostname": "c2c4e57c12c4",
. . .
docker inspect
命令会对容器进行详细的检查,然后返回其配置信息,包括名称、命令、网络配置以及很多有用的数据。
也可以用 -f
或者 --format
标志来选定查看结果,如代码清单3-33所示。
代码清单3-33 有选择地获取容器信息
$ sudo docker inspect --format='{{ .State.Running }}' daemon_dave
false
上面这条命令会返回容器的运行状态,示例中该状态为 false
。我们还能获取其他有用的信息,如容器IP地址,如代码清单3-34所示。
代码清单3-34 查看容器的IP地址
$ sudo docker inspect --format '{{ .NetworkSettings.IPAddress }}'
daemon_dave
172.17.0.2
提示
--format或者-f标志远非表面看上去那么简单。该标志实际上支持完整的Go语言模板。用它进行查询时,可以充分利用Go语言模板的优势。
也可以同时指定多个容器,并显示每个容器的输出结果,如代码清单3-35所示。
代码清单3-35 查看多个容器
$ sudo docker inspect --format '{{.Name}} {{.State.Running}}' \
daemon_dave bob_the_container
/daemon_dave false
/bob_the_container false
可以为该参数指定要查询和返回的查看散列(inspect hash)中的任意部分。
注意
除了查看容器,还可以通过浏览/var/lib/docker目录来深入了解Docker的工作原理。该目录存放着Docker镜像、容器以及容器的配置。所有的容器都保存在/var/lib/docker/containers目录下。
16 删除容器
如果容器已经不再使用,可以使用 docker rm
命令来删除它们,如代码清单3-36所示。
代码清单3-36 删除容器
$ sudo docker rm 80430f8d0921
80430f8d0921
注意
从Docker 1.6.2开始,可以通过给docker rm命令传递-f标志来删除运行中的Docker容器。这之前的版本必须先使用docker stop或docker kill命令停止容器,才能将其删除。
目前,还没有办法一次删除所有容器,不过可以通过代码清单3-37所示的小技巧来删除全部容器。
代码清单3-37 删除所有容器
$ sudo docker rm `sudo docker ps -a -q`
上面的 docker ps
命令会列出现有的全部容器, -a
标志代表列出所有容器,而-q
标志则表示只需要返回容器的ID而不会返回容器的其他信息。这样我们就得到了容器ID的列表,并传给了 docker rm
命令,从而达到删除所有容器的目的。
更多推荐
所有评论(0)