需要
失常状况下这种操作比拟反设计,须要审慎应用
有些时候咱们应用docker
的时候会须要用到宿主机命令操作,比方
- 执行
netplan apply
失效机器网络配置 - 查看宿主机网络信息应用
ifconfig
或者ip addr
- 从容器收回命令重启宿主机
具体实现
最简略的实现
应用docker
运行一个ubuntu
容器
进入容器之后执行nsenter
命令查看宿主机网络配置信息
$ sudo docker run -it --pid=host --privileged=true ubuntu /bin/bash# 进入容器外部之后执行/# nsenter -a -t 1 sh -c "ip addr"
实现原理
docker run
参数
--pid=host
- 应用宿主机命名空间,不便容器获取到宿主机所有过程信息
- 把宿主机的
/proc
文件夹挂载进入容器的/proc
门路,其中/proc/1
作为nsenter
的target
,作为容器向宿主机发送命令的要害局部
--privileged=true
- 使得
docker
容器有root
权限执行宿主机命令,确保从容器执行命令的时候不会产生权限有余谬误
nsenter
命令
nsenter
命令是一个能够在指定过程的命令空间下运行指定程序的命令
$ nsenter --help用法: nsenter [选项] [<程序> [<参数>...]]以其余程序的名字空间运行某个程序。选项: -a, --all enter all namespaces -t, --target <pid> 要获取名字空间的指标过程 -m, --mount[=<文件>] 进入 mount 名字空间 -u, --uts[=<文件>] 进入 UTS 名字空间(主机名等) -i, --ipc[=<文件>] 进入 System V IPC 名字空间 -n, --net[=<文件>] 进入网络名字空间 -p, --pid[=<文件>] 进入 pid 名字空间 -C, --cgroup[=<文件>] 进入 cgroup 名字空间 -U, --user[=<文件>] 进入用户名字空间 -S, --setuid <uid> 设置进入空间中的 uid -G, --setgid <gid> 设置进入名字空间中的 gid --preserve-credentials 不干预 uid 或 gid -r, --root[=<目录>] 设置根目录 -w, --wd[=<dir>] 设置工作目录 -F, --no-fork 执行 <程序> 前不 fork -Z, --follow-context 依据 --target PID 设置 SELinux 环境 -h, --help display this help -V, --version display version更多信息请参阅 nsenter(1)。
具体执行
$ nsenter -a -t 1 sh -c "ip addr"
-a
示意进入宿主机的所有命名空间-t 1
示意获取/proc/1
过程,就是pid=1
的过程,这个过程是docker
应用--pid=host
参数挂载进入容器外部的宿主机过程sh -c "ip addr"
就示意发送给宿主机的命令是ip addr
理论应用过程中如果呈现宿主机和容器命名空间不统一问题,次要产生起因是宿主机内核版本和容器
所默认的加载内核版本不统一
比方cgroup
是在Linux4.6
版本退出的,如果应用Ubuntu20
或者其余python3.10
等比拟新的镜像启动容器的时候,当nsenter
应用参数-a
,容器会加载所有命名空间,然而cgroup
命名空间在旧版本的零碎外面因为内核版本比拟旧,所以该命名空间是没有的,最终nsenter
命令就会报错
须要依照宿主机有的命名空间来调整nsenter
参数,能够调整如下
$ nsenter -m -u -i -n -p -t 1 sh -c "ip addr"
比方能够把-a
参数替换成-m -u -i -n -p
,明确指定进入mount
, UTS
,System V IPC
,网络
,pid
命名空间
这几个命名空间蕴含了绝大多数的空间环境,linux
的大部分命令都能够失常执行
命名空间阐明
namespace
是Linux
中一些过程的属性的作用域,应用命名空间,能够隔离不同的过程
Linux
在一直的增加命名空间,目前有
mount
:挂载命名空间,使过程有一个独立的挂载文件系统,始于Linux 2.4.19
ipc
:ipc
命名空间,使过程有一个独立的ipc
,包含音讯队列,共享内存和信号量,始于Linux 2.6.19
uts
:uts
命名空间,使过程有一个独立的hostname
和domainname
,始于Linux 2.6.19
net
:network
命令空间,使过程有一个独立的网络栈,始于Linux 2.6.24
pid
:pid
命名空间,使过程有一个独立的pid
空间,始于Linux 2.6.24
user
:user
命名空间,是过程有一个独立的user
空间,始于Linux 2.6.23
,完结于Linux 3.8
cgroup
:cgroup
命名空间,使过程有一个独立的cgroup
控制组,始于Linux 4.6
参考浏览
- nsenter命令简介
- Linux manual page
- docker官网文档