文章目录

  • 容器运行时的 -dit 选项
    • 默认:前台运行,stdout 和 stderr 转接出来,而stdin关了
    • 前台 -t
    • 前台 -i
    • 前台 -it
    • detach模式
    • 前后台切换
    • --attach
    • -i 和 -a
    • 注:bash 镜像

容器运行时的 -dit 选项

2021-06-22

docker run 命令的选项

  --attach , -a      Attach to STDIN, STDOUT or STDERR--detach , -d      Run container in background and print container ID--interactive , -i    Keep STDIN open even if not attached--tty , -t          Allocate a pseudo-TTY

docker exec 命令

  -d, --detach               Detached mode: run command in the background-i, --interactive          Keep STDIN open even if not attached-t, --tty                  Allocate a pseudo-TTY没有 -a --attach 选项
  • -a 可以多次指定 ,比如 -a stdin -a stdout
  • 不要同时使用 -t 和 -a stderr,因为 pty 本身的限制。pty

    Do not use the -t and -a stderr options together due to limitations in the pty implementation. All stderr in pty mode simply goes to stdout.

使用 bash:lastest 镜像,通过观察 /dev/fd/ 目录,查看容器控制台IO的打开关闭情况。

默认,dit组合是001,前台运行,无法输入,只能看到输出。
只有 -i 没有 -t,容器可以接受stdin的输入,也可以输出,但是通过管道,不是伪终端,是批处理模式,而不是交互模式。

默认:前台运行,stdout 和 stderr 转接出来,而stdin关了

默认 -d=false, -i=false, -t=false

默认 -d=false
-d=false时,默认-i=false,-t=false

dit:000

[work@cdh06 ~]$ docker run --rm  bash -c 'ls  -l /dev/fd/'
total 0
ls: /dev/fd/3: cannot read link: No such file or directory
lrwx------    1 root     root            64 Jun 22 09:11 0 -> /dev/null
l-wx------    1 root     root            64 Jun 22 09:11 1 -> pipe:[55404435]
l-wx------    1 root     root            64 Jun 22 09:11 2 -> pipe:[55404436]
lr-x------    1 root     root            64 Jun 22 09:11 3
[work@cdh06 ~]$ docker run --rm -d=false bash -c 'ls  -l /dev/fd/'
total 0
ls: /dev/fd/3: cannot read link: No such file or directory
lrwx------    1 root     root            64 Jun 22 09:11 0 -> /dev/null
l-wx------    1 root     root            64 Jun 22 09:11 1 -> pipe:[55409027]
l-wx------    1 root     root            64 Jun 22 09:11 2 -> pipe:[55409028]
lr-x------    1 root     root            64 Jun 22 09:11 3

此时,docker 使用了 -a STDERR -a STDOUT 选项。

前台 -t

dit: 001

$ docker run --rm -t bash -c 'ls  -l /dev/fd/'
total 0
lrwx------    1 root     root            64 Jun 22 10:14 0 -> /dev/pts/0
lrwx------    1 root     root            64 Jun 22 10:14 1 -> /dev/pts/0
lrwx------    1 root     root            64 Jun 22 10:14 2 -> /dev/pts/0

但是 stdin (/dev/fd/0)是得不到输入的。

前台 -i

dit:010

$ docker run --rm -i bash -c 'ls  -l /dev/fd/'
total 0
lr-x------    1 root     root            64 Jun 22 10:18 0 -> pipe:[55703397]
l-wx------    1 root     root            64 Jun 22 10:18 1 -> pipe:[55703398]
l-wx------    1 root     root            64 Jun 22 10:18 2 -> pipe:[55703399]

前台 -it

dit:011

$ docker run --rm -it bash -c 'ls  -l /dev/fd/'
total 0
lrwx------    1 root     root            64 Jun 22 10:19 0 -> /dev/pts/0
lrwx------    1 root     root            64 Jun 22 10:19 1 -> /dev/pts/0
lrwx------    1 root     root            64 Jun 22 10:19 2 -> /dev/pts/0

Q. -it 和 -t 没有看出来区别呀。
Ans: 有的。-i才能接收标准输入,前台运行时,只有-t没有-i,虽然会保持不退出,但无法输入任何命令和特殊字符,要退出,只有再开
一个窗口,docker rm -f 命令删除容器。

detach模式

-d=true 时,默认 -i=false,-t=true

后台模式,执行docker run 命令是看不到任何标准输出的,需要借助docker logs 命令。

$ docker run --rm -dit bash -c 'echo hello'
689d972fb889adf9e62e2a003e7976827cf0405233ffdc30dc54a70aa7e67aaa
$ docker run --name demo -d bash -c 'echo hello' && docker logs demo && docker rm demo
4a9aeb1cfdf5686cdfba00512b83d3e2e4635d989332c60f13aa63940ef36940
hello
demo
# -d 模式
$ docker run --name demo -d bash -c 'ls  -l /dev/fd/' && docker logs demo && docker rm demo
5d137c240eab57296702faec3ba155402ca72ed99086573951c0d07269b84dd3
ls: /dev/fd/3: cannot read link: No such file or directory
total 0
lrwx------    1 root     root            64 Jun 22 10:48 0 -> /dev/null
l-wx------    1 root     root            64 Jun 22 10:48 1 -> pipe:[55834607]
l-wx------    1 root     root            64 Jun 22 10:48 2 -> pipe:[55834608]
lr-x------    1 root     root            64 Jun 22 10:48 3
demo# -dit 模式
$ docker run --name demo -dit bash -c 'ls  -l /dev/fd/' && docker logs demo && docker rm demo
dda596f4c4edc1b8a720490b64bc9101bd17f97343075e5017efa69dab5ef9eb
total 0
lrwx------    1 root     root            64 Jun 22 10:49 0 -> /dev/pts/0
lrwx------    1 root     root            64 Jun 22 10:49 1 -> /dev/pts/0
lrwx------    1 root     root            64 Jun 22 10:49 2 -> /dev/pts/0
ls: /dev/fd/3: cannot read link: No such file or directory
lr-x------    1 root     root            64 Jun 22 10:49 3
demo
# -di
# ps: 其实,后台模式下,开启 STDIN 没有意义
$ docker run --name demo -di bash -c 'ls  -l /dev/fd/' && docker logs demo && docker rm demo
lr-x------    1 root     root            64 Jun 22 10:54 0 -> pipe:[55975007]
l-wx------    1 root     root            64 Jun 22 10:54 1 -> pipe:[55975008]
l-wx------    1 root     root            64 Jun 22 10:54 2 -> pipe:[55975009]
# -dt
$ docker run --name demo -dt bash -c 'ls  -l /dev/fd/' && docker logs demo && docker rm demo
lrwx------    1 root     root            64 Jun 22 10:58 0 -> /dev/pts/0
lrwx------    1 root     root            64 Jun 22 10:58 1 -> /dev/pts/0
lrwx------    1 root     root            64 Jun 22 10:58 2 -> /dev/pts/0

前后台切换

docker attach 命令可以把后台运行的容器挂到前台来。
如果容器运行时使用了 -it,那么可以使用 Ctrl-P Ctrl-Q 把容器重新放到后台,继续执行。
如果没有使用 -it,那么就只能使用 Ctrl-C 杀死容器才能退出。

–attach

使用 -a stdin 之后,就进入detach模式,还得按下Ctrl-D才能返回。
这是因为不指定 -a,容器默认有 -a stdout 和 -a stderr,而指定了-a stdin,默认绑定就没了,没了默认绑定就只有进入后台了。

$ docker run -a stdin --name  demo bash
a642ce63d68c8ac8edca395b51004a2f7ee635a9ecbac4ca28f31d2a8d721fef
<Ctrl-D>

分析一下,借助 ls -l /dev/fd/ 查看文件描述符,借助 cat 读取标准输入。

# 容器的标准输入并没有打开,但外部确实看到好像标准输入能读取
$ docker run -a stdin --name  demo bash -c 'ls -l /dev/fd/; cat'
4465e310ef751b79245b598b09d35b149fc5ee85002fb97d24ddcfae53fe95b9
hello, world
<Ctrl-D>
[work@cdh06 ~]$ docker logs demo
total 0
lrwx------    1 root     root            64 Jun 22 11:26 0 -> /dev/null
l-wx------    1 root     root            64 Jun 22 11:26 1 -> pipe:[56065531]
l-wx------    1 root     root            64 Jun 22 11:26 2 -> pipe:[56065532]
lr-x------    1 root     root            64 Jun 22 11:26 3
ls: /dev/fd/3: cannot read link: No such file or directory# 加上-i就通了。
$ docker rm -f demo
demo
[work@cdh06 ~]$ docker run -a stdin -i --name  demo bash -c 'ls -l /dev/fd/; cat'
28548534643ab2a6fde1ac7ef4393eca13e2671b95570a5ff898732f0f165fbf
hello
world
<Ctrl-D>[work@cdh06 ~]$ docker logs demo
total 0
ls: /dev/fd/3: cannot read link: No such file or directory
lr-x------    1 root     root            64 Jun 22 11:27 0 -> pipe:[56069724]
l-wx------    1 root     root            64 Jun 22 11:27 1 -> pipe:[56069725]
l-wx------    1 root     root            64 Jun 22 11:27 2 -> pipe:[56069726]
lr-x------    1 root     root            64 Jun 22 11:27 3
hello
world# -a stdout 和 -a stderr 指定至少一个,就不会进入后台
[work@cdh06 ~]$ docker run --rm -a stdout -a stderr bash -c 'ls -l /dev/fd/'
ls: /dev/fd/3: cannot read link: No such file or directory
total 0
lrwx------    1 root     root            64 Jun 22 11:49 0 -> /dev/null
l-wx------    1 root     root            64 Jun 22 11:49 1 -> pipe:[56124973]
l-wx------    1 root     root            64 Jun 22 11:49 2 -> pipe:[56124974]
lr-x------    1 root     root            64 Jun 22 11:49 3
[work@cdh06 ~]$ docker run --rm -a stdout  bash -c 'ls -l /dev/fd/'
total 0
lrwx------    1 root     root            64 Jun 22 11:49 0 -> /dev/null
l-wx------    1 root     root            64 Jun 22 11:49 1 -> pipe:[56128608]
l-wx------    1 root     root            64 Jun 22 11:49 2 -> pipe:[56128609]
lr-x------    1 root     root            64 Jun 22 11:49 3
[work@cdh06 ~]$ docker run --rm -a stderr  bash -c 'ls -l /dev/fd/'
ls: /dev/fd/3: cannot read link: No such file or directory
# 不论如何,stdout 和 stderr 的输出都可以通过logs没了查看
$ docker run --name demo -a stderr bash -c 'ls -l /dev/fd/'
ls: /dev/fd/3: cannot read link: No such file or directory
[work@cdh06 ~]$ docker logs demo
total 0
ls: /dev/fd/3: cannot read link: No such file or directory
lrwx------    1 root     root            64 Jun 22 11:54 0 -> /dev/null
l-wx------    1 root     root            64 Jun 22 11:54 1 -> pipe:[56138416]
l-wx------    1 root     root            64 Jun 22 11:54 2 -> pipe:[56138417]
lr-x------    1 root     root            64 Jun 22 11:54 3# Extend:甚至,交互模式的容器,其标准IO也可以用 docker logs 命令查看
$ docker run -it --name demo bash
bash-5.1# echo hello
hello
bash-5.1#
exit
[work@cdh06 ~]$ docker logs demo
bash-5.1# echo hello
hello
bash-5.1#
exit
# 由此,有时候交互模式卡顿,可能是日志阻塞了交互,可以使用异步日志
docker run --rm -it --log-opt mode=non-blocking --log-opt max-buffer-size=10m bash
docker run --rm -it bash

-i 和 -a

容器内的进程 P,docker 服务进程 D,命令行进程 S。
想要容器读取输入,必须做两点:

  1. 使用 -i 选项,把 P 的 STDIN 打开,打开的STDIN的另一头在进程D中。
  2. 使用 -a stdin 把 S 的标准输入对接到 P 的STDIN,通过 D 做中转。
  3. -i 会默认启用 -a stdin;但 -a stdin 却不会自动启用 -i。

注:bash 镜像

使用 bash 镜像的时候,

docker run bash -c 'ls -l /dev/fd/'

完整的格式应该写成

docker run bash bash -c 'ls -l /dev/fd/'
COPY docker-entrypoint.sh /usr/local/bin/
ENTRYPOINT ["docker-entrypoint.sh"]
CMD ["bash"]

而 docker-engrypoint.sh 就这一点。

#!/usr/bin/env bash
set -Eeuo pipefail# first arg is `-f` or `--some-option`
# or there are no args
if [ "$#" -eq 0 ] || [ "${1#-}" != "$1" ]; then# docker run bash -c 'echo hi'exec bash "$@"
fiexec "$@"

当指定 -c 的时候,脚本会自动补上 bash。

docker容器的前台后台运行相关推荐

  1. 【docker】Docker容器的两种运行模式(Foreground、Detached)

    文章目录 Docker容器进程有两种运行模式. 后台模式就是在后台运行,不会让当前进程卡主,你可以做其他事情,而前台模式会导致当前卡住,并输出日志至当前控制台. Foreground 前台模式(默认) ...

  2. Linux下前台/后台运行

    1. 启动时 以 & 结尾,后台运行 2.已经启动的程序, 按CRTL + z   //放到后台暂停 bg + %进程号,将程序放到后台运行 可通过jobs指令查看后台运行程序 bg + %进 ...

  3. Docker 容器默认root账号运行

    默认情况下,容器中的进程以 root 用户权限运行,并且这个 root 用户和宿主机中的 root 是同一个用户.听起来是不是很可怕,因为这就意味着一旦容器中的进程有了适当的机会,它就可以控制宿主机上 ...

  4. 验证docker容器相当轻量级Linux运行环境,每个容器内有属于自己的文件系统,容器之间相互隔离

    一.docker的三个重要概念 1.镜像:打包项目带上环境,即镜像 Docker镜像是一个特殊的文件系统,除了提供容器运行时所需的程序.库.资源.配置等文件外,还包含了一些为运行时准备的配置参数.镜像 ...

  5. Docker容器的安装并运行一个网页游戏

    文章目录 简介 安装 我的第一个容器 简介 Docker 是一个开源的应用容器引擎,基于 Go 语言 并遵从 Apache2.0 协议开源. Docker 可以让开发者打包他们的应用以及依赖包到一个轻 ...

  6. 3.docker创建容器 (docker容器命令)

    文章目录 1.[nginx 容器拉取](https://blog.csdn.net/weixin_43627706/article/details/121990040) 2.运行创建一个nginx容器 ...

  7. linux docker查找镜像文件,搜索/下载/构建自定义/删除Docker镜像,运行和删除Docker容器的方法...

    本文为你介绍的内容是Docker入门相关的操作方法:搜索Docker镜像.下载Docker镜像.运行Docker容器.构建自定义Docker镜像.删除容器.删除Docker镜像.以下给出的所有步骤均在 ...

  8. 实现Mac主机上的Docker容器中的图形界面显示(运行GUI应用)

    我有一个需求: 一方面,我需要在 Docker 容器环境下运行应用(因为有些环境在 Mac 下很难安装配置,并且希望环境干净隔离). 另一方面,容器中的应用又需要进行图形界面的显示. 由于 Docke ...

  9. Docker容器技术与应用(项目2 Docker容器安装和使用)

    项目2 Docker容器安装和使用 下面重点介绍Docker的安装,镜像Image.镜像仓库Registry和容器Container的使用和管理. 图2.1 Docker镜像.容器和仓库之间的主要操作 ...

  10. Docker: 容器与镜像

    文章目录 1.docker 环境搭建 1.1.docker 安装 1.1.1.centos 安装 1.1.2.ubuntu 安装 1.2.添加到 docker 组 1.3.docker 镜像源 2.d ...

最新文章

  1. Theano - 循环
  2. ANSYS滑块导轨配合方法
  3. 程序员的个人发展注意事项
  4. Caffe下自己的数据训练和测试
  5. python使用curses库获取控制台的键盘输入(如上下左右)
  6. boost::hana::curry用法的测试程序
  7. ssh 远程登录不用密码 ssh-keygen -t rsa
  8. Ext.js4.x 的面板中嵌入UEditor编辑器
  9. MATLAB-矩阵基本语法知识
  10. P7515-[省选联考 2021A卷]矩阵游戏【差分约束】
  11. 清除浮动造成的影响的解决方案总结
  12. [前端]网页网络分析及前端网络优化
  13. linux jzmq编译,Linux下ps aux解释
  14. 剑指offer——面试题39:二叉树的深度
  15. .netcore 2.0 mysql_搭建连接MySql的三层架构的ASP.NetCore2.0的WebApi
  16. 计算机考研人工智能选什么方向,我想报人工智能方向的研究生,应该选取什么专业?...
  17. win8激活时出现”错误代码:0×8007007B 错误描述:文件名、目录名或卷标语法不正确“解决方法
  18. java猴子分桃问题_通俗易懂、简单粗暴得解决猴子分桃问题
  19. aria2 txt导入_使用Aria2完成下载任务
  20. html字体插件,20款jQuery CSS文字特效插件(有图有真相)

热门文章

  1. 无限循环病毒HTML,红包群无限循环病毒式裂变引流
  2. java 月的天数_Java获取某月天数
  3. win7 计算机设置命令,win7系统如何设置自动关机?
  4. MTK 人工智能生态系统 <一> 简介
  5. KK集团冲刺上市背后:亏损规模连年飙升,KK馆贡献占比正在衰减
  6. 科学计算与Matlab笔记:第4章:Matlab绘图
  7. 多项式时间 P问题NP问题
  8. 泡泡龙游戏开发系列教程(五)
  9. 二维码设备巡检解决方案
  10. 唯冠也很苦!赢了苹果也付不出律师费