上次我检查时,Docker没有任何方法让容器访问主机串行或USB端口。有什么技巧可以做到吗?


当前回答

在当前版本的Docker中,你可以使用——device标志来实现你想要的,而不需要访问所有的USB设备。

例如,如果你想在Docker容器中只使/dev/ttyUSB0可访问,你可以这样做:

docker run -t -i --device=/dev/ttyUSB0 ubuntu bash

其他回答

还有一种更简单的共享usb设备的方法,没有——privileged标志。这样做:

Docker运行…——device=/dev/bus/usb——device=/dev/usb <container> .使用实例

除了上面的答案,对于那些想要快速使用外部USB设备(HDD,闪存驱动器)在docker内部工作,而不使用特权模式的人:

在主机上找到你的设备的devpath:

sudo fdisk -l

您可以很容易地从列表中识别您的驱动器的容量。复制该路径(在下例中为/dev/sda2)。

Disque /dev/sda2 : 554,5 Go, 57151488 octets, 111624 secteurs
Unités : secteur de 1 × 512 = 512 octets
Taille de secteur (logique / physique) : 512 octets / 512 octets
taille d'E/S (minimale / optimale) : 512 octets / 512 octets

挂载这个devpath(最好是/media):

sudo mount <drive path> /media/<mount folder name>

然后你可以使用它作为docker运行的参数:

docker run -it -v /media/<mount folder name>:/media/<mount folder name>

或者在docker中合成volumes:

services:
  whatevermyserviceis:
    volumes:
      - /media/<mount folder name>:/media/<mount folder name>

现在,当您运行并进入容器时,您应该能够访问容器中的驱动器/media/<挂载文件夹名>

免责声明:

这可能不适用于串行设备,如网络摄像头等。 我只对USB存储驱动器进行了测试。 如果您需要定期重新连接和断开设备,这 方法将会很烦人,并且除非重置挂载路径并重新启动容器,否则将无法工作。 我使用docker 17.06 +在文档中规定

--device works until your USB device gets unplugged/replugged and then it stops working. You have to use cgroup devices.allow get around it. You could just use -v /dev:/dev but that's unsafe as it maps all the devices from your host into the container, including raw disk devices and so forth. Basically this allows the container to gain root on the host, which is usually not what you want. Using the cgroups approach is better in that respect and works on devices that get added after the container as started.

在Docker中访问USB设备而不使用——特权

这有点难粘贴,但简而言之,你需要获得你的角色设备的主编号,并将其发送到cgroup:

188是/dev/ttyUSB*的主编号,可以通过'ls -l'获得。你的系统和我的系统可能不同:

root@server:~# echo 'c 188:* rwm' > /sys/fs/cgroup/devices/docker/$A*/devices.allow  
(A contains the docker containerID)

然后像这样启动你的容器:

docker run -v /dev/bus:/dev/bus:ro -v /dev/serial:/dev/serial:ro -i -t --entrypoint /bin/bash debian:amd64

如果不这样做,容器启动后任何新插入或重新启动的设备将获得一个新的总线ID,并且将不允许访问容器。

有几个选择。你可以使用——device标志,用户可以在没有——特权模式的情况下访问USB设备:

docker run -t -i --device=/dev/ttyUSB0 ubuntu bash

或者,假设您的USB设备在主机/dev/bus/usb上可用,并且驱动程序正在工作等,您可以使用特权模式和volumes选项将其挂载到容器中。例如:

docker run -t -i --privileged -v /dev/bus/usb:/dev/bus/usb ubuntu bash

注意,顾名思义,——privileged是不安全的,应该小心处理。

在当前版本的Docker中,你可以使用——device标志来实现你想要的,而不需要访问所有的USB设备。

例如,如果你想在Docker容器中只使/dev/ttyUSB0可访问,你可以这样做:

docker run -t -i --device=/dev/ttyUSB0 ubuntu bash