Linux 技术应用实践-调用宿主机命令检查docker容器网络、进程状态

本文介绍了如何利用Linux namespace技术解决在Docker容器中缺少命令的问题,特别是网络抓包和进程监控。通过nsenter和unshare命令,可以进入容器的Network、PID和Mount namespace,实现宿主机命令如tcpdump、ps、top在容器内的执行,而无需在容器内安装这些工具,同时避免影响宿主机的proc文件系统。
摘要由CSDN通过智能技术生成

背景

最近偶然听了几堂极客时间的云原生免费公开课程,首次接触到了Linux namespace技术,并了解到这正是现在风头正劲的容器技术基石,引起了自己探究一二的兴趣,结合课程+网络搜索+实践操作,也算有了一些初步的了解,这里记录、总结一些学习过程。

Linux namespace简介

namespace技术网上的介绍已经很多了,这里不做过多赘述,简单总结namespace是Linux 内核提供的支持内核资源隔离的关键技术,目前包含以下7类namespace:
Namespace 变量 隔离资源
Cgroup CLONE_NEWCGROUP Cgroup 根目录
IPC CLONE_NEWIPC System V IPC, POSIX 消息队列等
Network CLONE_NEWNET 网络设备,协议栈、端口等
Mount CLONE_NEWNS 挂载点
PID CLONE_NEWPID 进程ID
User CLONE_NEWUSER 用户和group ID
UTS CLONE_NEWUTS Hostname和NIS域名
本文中主要涉及到的是Network+PID+Mount三个namespace。

容器运行时缺少必要命令问题与解决方案

下载使用docker官方提供的基础操作系统镜像-本例中为deiban--时会发现很多命令都默认没有安装--比如网络抓包tcpdump、甚至进程信息查看ps/top等,直觉上的办法只能进入容器内部逐个安装。然而如果每次运行新容器都需要安装一遍相关工具包的话未免有些繁琐,另外如果只是启动初期临时使用一下这些工具调试,之后便不再需要,额外安装这些工具其实也不必要的增大了容器本身的复杂度。
针对这一问题,其实linux提供了nsenter、unshare命令用于进入容器进程所属Network、PID、Mount 等namespace执行宿主机命令,从而达到无需在容器中安装命令,直接使用宿主机相应命令的目的,以下以tcpdump/ps/top三个命令的执行为例进行进行介绍。

利用宿主机tcpdump命令对docker容器进行抓包

利用nsenter命令可以指定目标namespace,并在其中执行对应命令。
以下命令先运行一个debian基础镜像的容器,而后在其中执行ip addr命令查看网络配置,并尝试执行tcpdump命令抓包

~# docker run -it --name ns_test_net   -d debian:stretch
d221b13a5fbcbf23a981a3067847b743081fff20ae05e6892b8744546cb1b148
~# docker ps
CONTAINER ID        IMAGE               COMMAND             CREATED             STATUS              PORTS               NAMES
d221b13a5fbc        debian:stretch      "bash"              9 seconds ago       Up 6 seconds                            ns_test_net
~# docker exec -it ns_test_net bash
root@d221b13a5fbc:/# ip addr
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
2: tunl0@NONE: <NOARP> mtu 1480 qdisc noop state DOWN group default qlen 1
    link/ipip 0.0.0.0 brd 0.0.0.0
23: eth0@if24: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default
    link/ether 02:42:ac:11:00:03 brd ff:ff:ff:ff:ff:ff link-netnsid 0
    inet 172.17.0.3/16 brd 172.17.255.255 scope global eth0
       valid_lft forever preferred_lft forever
root@d221b13a5fbc:/# tcpdump dump -i any -nvv
bash: tcpdump: command not found

可以看到报错command not found,此时可以简单通过nsenter使用宿主机命令进入容器所属namespace执行相关命令:
通过ip addr 查看容器网络配置,通过tcpdump 尝试抓包

~# docker inspect -f {
  {.State.Pid}} ns_test_net # 获取容器进程在宿主机上的pid
9164
 nsenter -t 9164 -n ip addr # -t指定容器进程pid,-n指定使用对应pid的Networ
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值