我很天真地希望此命令在运行中的容器中运行bash shell:
br />
docker run "id of running container" /bin/bash


因此,如果我想在正在运行的容器中运行bash shell(例如,出于诊断目的)

我必须在其中运行SSH服务器吗并通过ssh登录?

评论

docker run CONTAINER计划在1.0中实现

从docker 1.3开始,您应该按照此答案所述进行操作

只是docker attach container_name

如今,第二个答案似乎比接受的答案好得多-您会重新考虑更改接受的答案吗?

我提出了一个单独的命令docker shell github.com/moby/moby/issues/41702

#1 楼

编辑:现在您可以使用docker exec -it "id of running container" bash(doc)

以前,此问题的答案是:

如果确实需要并且您处于调试环境中,则可以执行这是:sudo lxc-attach -n <ID>
请注意,ID必须是完整的ID(docker ps -notrunc)。 ,很快就会将其替换为-notrunc

评论


你为什么反对呢?

–最大L。
13年7月30日在15:05

我建议不要这样做,因为1)它需要一个非常新的内核,2)您正在docker之外做事,因此您将无法对其进行跟踪(日志,附加等)。另外,docker现在可能会使用lxc,但没有任何保证,它将永远使用。

–裂纹
13年7月30日在21:57

尝试更新至0.7.6。 Docker现在仍在使用lxc,lxc-attach应该可以正常工作。我只是仔细检查了一下,对我有用。 (请注意,它不适用于3.8之前的内核)。

–裂纹
2014年1月16日19:26

从0.9开始,默认情况下Docker不再与LXC一起运行。您必须使用docker -d -e lxc启动docker deamon

–kevzettler
2014年3月16日下午5:16

Max L.,您的用例可以通过数据量解决。未经测试的示例:1)使用nginx在数据量中登录容器运行数据:docker run -v / var / log / nginx -name somename imagename命令; 2)运行另一个容器以查看数据卷内容:docker运行-volumes-from somename -i -t busybox / bin / sh。

–ciastek
2014年6月12日在11:27

#2 楼

对于docker 1.3,有一个新命令docker exec。这使您可以输入正在运行的docker:

docker exec -it "id of running container" bash


评论


这对我来说很棒。对docker run很有帮助。

–oraserrata
2014年12月3日,3:10

如果我在执行一个正在运行的容器时执行更改并希望在线反映更改怎么办?最佳做法是什么?

–mediaroot
2015年10月3日在20:39

很有用。谢谢

–luongnv89
15年11月19日在14:06

使用docker ps获取正在运行的实例的ID

–μon
17年1月1日在21:43

注意:该容器可能没有bash(»exec:“ bash”:找不到可执行文件«)。使用docker inspect 来查看可用的shell。例如。运行docker exec -it <容器ID> / bin / sh。

–pixelbrackets
17年4月21日在9:26



#3 楼

只需执行

docker attach container_name


如注释中所述,要从容器中分离而不停止容器,请键入Ctrlpthen Ctrlq。

评论


谢谢!!它有帮助。关于实际问题,我想补充一点。使用调试我们的容器后,docker attach container_name使用ctrl p和ctrl q而不是exit。退出命令将停止容器,因为ctrlp和ctrl q只是分离该容器并使其保持运行

–凤凰
2014年8月6日17:15



#4 楼

由于情况正在发生变化,目前,推荐的访问运行容器的方法是使用nsenter。您可以在此github存储库中找到更多信息。但是一般来说,您可以使用如下所示的nsenter: />可以在JérômePetazzoni的博客条目中找到关于该主题的很好的解释:
为什么不需要在Docker容器中运行sshd

评论


不幸的是,使用这种方法会弄乱环境变量(如果您想检查链接创建的变量)。我建议做源/ proc / * / environ。

– Tomas Tomecek
2014年10月15日上午8:12

#5 楼

您无法运行的第一件事

docker run "existing container" command


因为此命令期望的是图像而不是容器,并且总会产生新的容器(所以您不能使用该容器想看看)

我同意以下事实:使用docker,我们应该以一种不同的方式推动自己进行思考(因此,您应该找到一些方法,从而无需登录容器) ,但我仍然发现它很有用,这就是我的解决方法。

我通过DEAMON模式下的主管运行命令。

然后我执行所谓的docker_loop.sh <内容基本上是这样的:

#!/bin/bash
/usr/bin/supervisord
/usr/bin/supervisorctl
while ( true )
    do
    echo "Detach with Ctrl-p Ctrl-q. Dropping to shell"
    sleep 1
    /bin/bash
done


它的作用是允许您“附加”到容器并通过supervisorctl界面显示停止/启动/重新启动并检查日志。
如果这还不够,您可以Ctrl+D并放入一个外壳中,使您可以像正常系统一样窥视一下。

也请入帐该系统的安全性不如没有外壳的容器,因此请采取所有必要步骤来固定容器。

#6 楼

请密切注意此请求:https://github.com/docker/docker/pull/7409

实现即将推出的docker exec <container_id> <command>实用程序。当可用时,例如在正在运行的容器内启动和停止ssh服务。正在运行。
https://gist.github.com/ubergarm/ed42ebbea293350c30a6

评论


docker exec登陆Docker 1.3,因此现在可以在运行的容器中创建并加入新的shell会话

– foz
14-10-27在11:12

#7 楼

您可以使用

docker exec -it <container_name> bash


#8 楼

这是我的解决方案
在Dockerfile中:
 # ...
RUN mkdir -p /opt
ADD initd.sh /opt/
RUN chmod +x /opt/initd.sh
ENTRYPOINT ["/opt/initd.sh"]
 

initd.sh文件中
 #!/bin/bash
...
/etc/init.d/gearman-job-server start
/etc/init.d/supervisor start
#very important!!!
/bin/bash
 

构建映像后,您可以使用execattach使用两个选项:
 docker run --name $CONTAINER_NAME -dt $IMAGE_NAME
 

然后
docker exec -it $CONTAINER_NAME /bin/bash

,并使用CTRL + D分离


使用附加并运行:
 docker run --name $CONTAINER_NAME -dit $IMAGE_NAME
 

然后
 docker attach $CONTAINER_NAME
 

,并使用CTRL + P和CTRL + Q分离
注意:选项之间的区别在于参数-i



#9 楼

实际上,有一种方法可以在容器中放入外壳。

假设您的/root/run.sh启动了流程,流程管理器(主管)或其他功能。 -screen技巧:

# Spawn a screen with two tabs
screen -AdmS 'main' /root/run.sh
screen -S 'main' -X screen bash -l
screen -r 'main'


现在,您的守护进程在选项卡0中,而交互式外壳程序在选项卡1中。/root/runme.sh随时可以查看容器内部发生了什么。

另一个建议是使用所有必要的工具(包括此屏幕技巧)在生产映像的顶部创建“开发包”映像。

#10 楼

有两种方法。

使用Attach

$ sudo docker attach 665b4a1e17b6 #by ID


使用exec

$ sudo docker exec - -t 665b4a1e17b6 #by ID


#11 楼

如果目标是检查应用程序的日志,则此文章将显示启动tomcat并将该日志尾随CMD的一部分。 Tomcat日志可在主机上使用'docker logs containerid'使用。

http://blog.trifork.com/2013/08/15/using-docker-to-ficiently-create-multiple -tomcat-instances /

#12 楼

运行容器时,这很有用。您不需要引用container_id。

docker run --name container_name yourimage docker exec -it container_name bash

#13 楼

首先,通过

docker ps


获取所需容器的容器ID,您将得到如下内容: />现在复制此容器ID并运行以下命令:

CONTAINER ID        IMAGE                  COMMAND             CREATED             STATUS                          PORTS                    NAMES
3ac548b6b315        frontend_react-web     "npm run start"     48 seconds ago      Up 47 seconds                   0.0.0.0:3000->3000/tcp   frontend_react-web_1



#14 楼

在开发容器时,也许您像我一样误导了关于VM的思考。我的建议:尽量不要。

容器就像其他任何过程一样。确实,您可能想将它们“附加”用于调试目的(例如/ proc // env或strace -p),但这是一个非常特殊的情况。

通常,您只是“运行”该过程,因此,如果您要修改配置或阅读日志,只需创建一个新容器,并确保通过共享目录,写入stdout(这样docker日志可以工作)或类似的方式在其外部写入日志。

出于调试目的,您可能需要启动外壳,然后启动代码,然后按CTRL-p + CTRL-q保持外壳完好无损。这样,您可以使用以下方法重新连接:

docker attach <container_id>


如果要调试容器是因为它正在做您没想到的事情,请尝试对其进行调试:https ://serverfault.com/questions/596994/how-can-i-debug-a-docker-container-initialization

评论


这是完全错误的。能够内省运行您的应用程序的LXC名称空间并不是“非常特殊的情况”,对于任何开发人员来说,这都是常见的/日常的活动。

–sleepycal
2014年8月5日18:21

@sleepycal“任何开发人员”听起来有点偏颇。无论如何,我都会使用进程的自省,所以同样的事情也适用于容器。这就是调试背后的想法。您将调试器附加到该进程(可能具有CLI)。认为您“已”登录到容器听起来仍然对我产生误解。

–estani
2014年8月6日在8:03

#15 楼

不行。这是不可能的。如果需要,请使用supervisord之类的东西来获取ssh服务器。虽然,我绝对质疑这个需求。