在容器中执行新命令
描述
isula exec命令用于正在运行的容器中运行一个新命令。新执行的命令将在容器的默认目录中运行。如果基础镜像指定了自定义目录,则将使用该目录。
用法
isula exec [OPTIONS] CONTAINER COMMAND [ARG...]
参数
exec命令支持参数参考下表。
表 1 exec命令参数列表
约束限制
- isula exec 不指定任何参数时,会默认使用-it参数, 表示分配一个伪终端,以交互式的方式进入容器
当使用isula exec 执行脚本,在脚本中执行后台进程时,需使用nohup标志忽略SIGHUP信号。
使用isula exec运行脚本,在脚本中运行后台进程需使用nohup标志。否则内核会在exec执行的进程(session首进程)退出时,向后台执行的进程发送SIGHUP信号,导致后台进程退出,出现僵尸进程。
isula exec 进入容器进程后,不能执行后台程序,否则会出现卡死现象。
isula exec执行后台进程的方式如下:
- 使用isula exec进入容器终端,isula exec container_name bash
- 进入容器后,执行 script &
- 执行exit,导致终端卡死
isula exec 进入容器后,执行后台程序卡住的原因为isula exec进入容器运行后台while1程序,当bash退出时,while1程序并不会退出,变为孤儿进程由1号
进程接管,while1程序是由容器的初始bash进程fork &exec执行的,while1进程复制了bash进程的文件句柄,导致bash退出时,句柄并未完全关闭,导致
console进程收不到句柄关闭事件,epoll_wait卡住,进程不退出。
isula exec 不能用后台方式执行,否则可能会出现卡死现象。
isula exec后台执行的方式如下:
使用isula exec 脚本 & 的方式后台执行exec,如:isula exec container_name script & ,isula exec 后台执行,执行的脚本中不断cat某一文件,正常时在当前终端有输出,如果在当前终端执行回车操作,客户端会因读IO失败而退出读stdout的动作,使终端不再输出,服务端由于进程仍然在cat文件,会继续往fifo的buffer里写入数据,当缓存写满时,容器内进程会卡死在write动作上。
轻量级容器使用exec执行带有管道操作的命令时,建议使用/bin/bash -c 方式执行该命令。
典型应用场景:
使用isula exec container_name -it ls /test | grep “xx” | wc -l,用于统计test目录下xx的文件个数,因exec执行的为”ls /test”,其输出通过管道进行grep、wc 处理。exec执行的为”ls /test”的输出会换行,再针对该输出进行处理时,结果有误。
原因:使用exec 执行ls /test,输出带有换行,针对该输出进行“| grep “xx” | wc -l“,处理结果为2(两行)
[root@localhost ~]# isula exec -it container ls /test
xx xx10 xx12 xx14 xx3 xx5 xx7 xx9
xx1 xx11 xx13 xx2 xx4 xx6 xx8
[root@localhost ~]#
建议处理方式:使用run/exec执行带有管道操作的命令时,使用/bin/bash -c 执行命令,在容器中执行管道操作。
[root@localhost ~]# isula exec -it container /bin/sh -c "ls /test | grep "xx" | wc -l"
15
[root@localhost ~]#
禁止使用echo的方式向exec命令的stdin输入数据,会导致客户端卡死。应该直接将echo的值作为命令行参数传给容器
``` [root@localhost ~]# echo ls | isula exec 38 /bin/sh
^C
[root@localhost ~]#
```
上述命令可能出现客户端卡死现象,这是由于上述命令相当于往stdin输入ls,随后EOF被读取,客户端不再发送数据,等待服务端退出,但是服务端无法区分客户端是否需要继续发送数据,因而服务端卡在read数据上,最终导致双方均卡死。
正确的执行方式为:
```
[root@localhost ~]# isula exec 38 ls
bin dev etc home proc root sys tmp usr var
```
示例
在运行中的容器中,执行echo命令
$ isula exec c75284634bee echo "hello,world"
hello,world