基于GUI的环境的Docker?

问题

我有一组客户机,它们是企业Web应用程序的一部分。 每台机器运行相同的软件,这是一个基于PyQT的networking客户端连接到服务器。 这个客户端软件定期更新,我想有一些configuration/供应工具,允许在每台机器上具有相同的环境,因此可以方便地在每台客户机上部署和configuration软件。

问题是我试图使用厨师,但是要真正维持厨师的知识和技能(我们没有一个专门的操作人员)需要花费很大的精力,而且如果某个第三方存储库不再存在,厨师食谱可能会失败可用 (这是一个主要的塞子)。

我想尝试Docker来解决这个问题,但我仍然不知道是否可以设置允许一些基于GUI的软件运行的图像/容器。

是否有可能使用Docker为基于GUI的应用程序(PyQt / QT)开发/生产环境? 如果是的话,接下来要做的第一步是什么?

目前这个问题没有回答,但在Google上排名很高。 其他的答案大多是正确的,但是有一些告诫我已经学会了很多,我想省去一些麻烦。

Nasser Alshammari给出的答案是在Docker容器中运行GTK应用程序的最简单(也是最快)的方法 – 只需将X服务器的套接字作为Docker卷装入,然后告诉Docker使用它。

docker run -v /tmp/.X11-unix:/tmp/.X11-unix -e DISPLAY=unix$DISPLAY TheImage 

(我还build议传递-u <username-within-container>标志,因为以root身份运行X11应用程序并不总是有效,通常不build议使用, 特别是在共享会话时)。

这将适用于xterm等应用程序以及基于GTK的应用程序。 例如,如果您使用Firefox(基于GTK)来尝试此操作,它将起作用(请注意,如果您已经在主机上运行Firefox,它将在主机中打开一个新窗口,而不是打开Firefox的一个新实例从容器内)。

但是 ,您的回答特别针对PyQT。 事实certificate,Qt不支持以这种方式共享X会话 (或者至less不支持)。

如果您尝试以这种方式运行基于QT的应用程序,则可能会出现如下错误:

 X Error: BadAccess (attempt to access private resource denied) 10 Extension: 140 (MIT-SHM) Minor opcode: 1 (X_ShmAttach) Resource id: 0x12d X Error: BadShmSeg (invalid shared segment parameter) 148 Extension: 140 (MIT-SHM) Minor opcode: 5 (X_ShmCreatePixmap) Resource id: 0xb1 X Error: BadDrawable (invalid Pixmap or Window parameter) 9 Major opcode: 62 (X_CopyArea) Resource id: 0x2c0000d X Error: BadDrawable (invalid Pixmap or Window parameter) 9 Major opcode: 62 (X_CopyArea) Resource id: 0x2c0000d 

我说“可能”是因为我没有用足够多的Qt应用程序来testing这个方法,或者深入研究Qt源代码,找出为什么不支持。 YMMV,你可能会很幸运,但是如果你想从一个Docker容器中运行一个基于Qt的应用程序,你可能不得不采用“老式”的方法,

  1. 在容器中运行sshd,打开X11转发,然后使用ssh -X (更安全)或ssh -Y (不太安全, 在完全信任容器化应用程序时使用)连接到容器。

  2. 在容器中运行VNC,并使用VNC客户端从主机连接到VNC。

在这两个选项之间,我会推荐第一个,但是看看哪个最适合您的情况。

在Docker容器中运行GUI应用程序有许多解决scheme。 您可以使用SSH或VNC。 但他们增加了一些开销和延迟。 我发现的最好方法就是将主机中X服务器使用的文件作为卷传递给容器。 喜欢这个:

 docker run -v /tmp/.X11-unix:/tmp/.X11-unix -e DISPLAY=unix$DISPLAY TheImage 

然后,所有的GUI应用程序将从容器运行。

希望这可以帮助!

我设法在一个容器中运行xeyes,并看到在容器外部运行的X服务器中的“窗口”。 就是这样:

我使用Xephyr来运行一个嵌套的X服务器。 这是没有必要的,但大多数Linux桌面不允许默认运行远程应用程序( 这里是如何“修复”在Ubuntu上)。

安装Xephyr:

 $ sudo apt-get install xserver-xephyr 

运行Xephyr:

 $ Xephyr -ac -br -noreset -screen 800x600 -host-cursor :1 

这将创build一个新的800×600窗口,作为X服务器。

find你的机器的“外部”地址。 这是X服务器正在运行的位置:

 $ ifconfig docker0 Link encap:Ethernet HWaddr 56:84:7a:fe:97:99 inet addr:172.17.42.1 Bcast:0.0.0.0 Mask:255.255.0.0 inet6 addr: fe80::5484:7aff:fefe:9799/64 Scope:Link UP BROADCAST MULTICAST MTU:1500 Metric:1 RX packets:133395 errors:0 dropped:0 overruns:0 frame:0 TX packets:242570 errors:0 dropped:0 overruns:0 carrier:0 collisions:0 txqueuelen:0 RX bytes:9566682 (9.5 MB) TX bytes:353001178 (353.0 MB) lo Link encap:Local Loopback inet addr:127.0.0.1 Mask:255.0.0.0 inet6 addr: ::1/128 Scope:Host UP LOOPBACK RUNNING MTU:65536 Metric:1 RX packets:650493 errors:0 dropped:0 overruns:0 frame:0 TX packets:650493 errors:0 dropped:0 overruns:0 carrier:0 collisions:0 txqueuelen:0 RX bytes:2506560450 (2.5 GB) TX bytes:2506560450 (2.5 GB) wlan0 Link encap:Ethernet HWaddr c4:85:08:97:b6:de inet addr:192.168.129.159 Bcast:192.168.129.255 Mask:255.255.255.0 inet6 addr: fe80::c685:8ff:fe97:b6de/64 Scope:Link UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1 RX packets:6587370 errors:0 dropped:1 overruns:0 frame:0 TX packets:3716257 errors:0 dropped:0 overruns:0 carrier:0 collisions:0 txqueuelen:1000 RX bytes:7405648745 (7.4 GB) TX bytes:693693327 (693.6 MB) 

不要使用127.0.0.1! 你可以使用任何其他的。 我将使用172.17.42.1。

使用以下内容创build一个Dockerfile:

 FROM ubuntu RUN apt-get update RUN apt-get install -y x11-apps CMD ["/usr/bin/xeyes"] 

build立它:

 $ docker build -t xeyes . 

并运行它:

 $ docker run -e DISPLAY=172.17.42.1:1.0 xeyes 

请注意,我将DISPLAY环境variables设置为我想要查看的位置。

您可以使用相同的技术将显示redirect到任何X服务器。

您可以使用subuser来打包您的GUI应用程序。 它也很好的支持更新应用程序。 你可以把你的Dockerfiles放在一个git仓库中,然后在每个客户端上运行subuser update all来重build需要修改的镜像。

最近我试图在Docker中运行PyQt5应用程序。 我学到的是,你不能以root身份运行应用程序(你必须创build普通用户)。 当您想要在应用程序中播放audio/video时,您必须运行带有“audio”组的docker容器并挂载audio设备。 所以要运行我的应用程序,我使用这个:

 docker run -it \ -v /tmp/.X11-unix:/tmp/.X11-unix \ -v $(pwd)/test:/app \ -e DISPLAY=$DISPLAY \ -u myusername \ --group-add audio \ --device /dev/snd \ fadawar/docker-pyqt5-qml-qtmultimedia python3 /app/hello.py 

我花了一些时间,直到我找出了需要添加到我的容器来运行PyQt应用程序的包,所以我创build了几个Dockerfiles(使用简单的演示应用程序),以使其他人更容易:

Python 3 + PyQt5: https : //github.com/fadawar/docker-pyqt5

Python 3 + PyQt5 + QML + QtMultimedia: https : //github.com/fadawar/docker-pyqt5-qml-qtmultimedia

Interesting Posts