루트 없는 모드에서 실행할 때 Docker가 호스트에 어떻게 연결됩니까?

루트 없는 모드에서 실행할 때 Docker가 호스트에 어떻게 연결됩니까?

현재 문서에 따라 루트 없는 모드에서 docker 데몬을 실행하려고 합니다.https://docs.docker.com/engine/security/rootless/

netcat명령은 "일반적인 방법"으로 실행될 때 작동 하지만 docker예를 들면 다음과 같습니다
sudo docker run --rm -it --name custom <options> <image> bash.

(사용하려는 도커 이미지에 따라 netcat이 단계에서 컨테이너 내부에 패키지를 설치해야 할 수도 있습니다.)

root@a390456c8d0b:/# nc -vz 172.17.0.1 5432
Connection to 172.17.0.1 5432 port [tcp/postgresql] succeeded!

루트 없는 모드에서는 작동하지 않습니다.

root@a390456c8d0b:/# nc -vr 172.17.0.1 5432
nc: connect to 172.17.0.1 port 5432 (tcp) failed: Connection refused

172.17.0.1게이트웨이 는 docker가 새로운 루트 없는 모드가 아닌 일반적인 방식(sudo 사용)으로 실행될 때만 사용 가능/사용되는 것 같습니다 . 그러나 이것은 단지 추측일 뿐이다.

이 문제를 해결하는 방법과 루트 없는 Docker 컨테이너에서 호스트 시스템(Ubuntu 21.10/22.04 dev)의 포트를 ping하는 방법을 아는 사람이 있습니까? (이 예에서는 기본 포트 5432에서 postgres에 핑을 보내고 있지만 이는 귀하가 선택하는 어떤 포트라도 될 수 있습니다.)

정보:

$ docker --version
Docker version 20.10.12, build e91ed57

$ uname -mor
5.13.0-19-generic x86_64 GNU/Linux

루트 없는 상태에서 docker 서비스의 상태는 다음과 같습니다.

$ systemctl --user status docker
● docker.service - Docker Application Container Engine (Rootless)
     Loaded: loaded (/home/sk/.config/systemd/user/docker.service; disabled; vendor preset: enabled)
     Active: active (running) since Sun 2022-01-02 21:59:07 CET; 25min ago
       Docs: https://docs.docker.com/go/rootless/
   Main PID: 37085 (rootlesskit)
      Tasks: 58
     Memory: 57.5M
        CPU: 5.553s
     CGroup: /user.slice/user-1000.slice/[email protected]/app.slice/docker.service
             ├─37085 rootlesskit --net=slirp4netns --mtu=65520 --slirp4netns-sandbox=auto --slirp4netns-seccomp=auto --disable-host-loopback --port-driver=builtin --copy->
             ├─37096 /proc/self/exe --net=slirp4netns --mtu=65520 --slirp4netns-sandbox=auto --slirp4netns-seccomp=auto --disable-host-loopback --port-driver=builtin --co>
             ├─37114 slirp4netns --mtu 65520 -r 3 --disable-host-loopback --enable-sandbox --enable-seccomp 37096 tap0
             ├─37121 dockerd
             ├─37143 containerd --config /run/user/1000/docker/containerd/containerd.toml --log-level info
             └─37393 /usr/bin/containerd-shim-runc-v2 -namespace moby -id a370455c8d0bc3e2fd796e788d52d4315c06fc44befe38aa8eb5466f1128e787 -address /run/user/1000/docker/>

Jan 02 21:59:07 sk-Laptop dockerd-rootless.sh[37121]: time="2022-01-02T21:59:07.957623453+01:00" level=warning msg="Unable to find io controller"
Jan 02 21:59:07 sk-Laptop dockerd-rootless.sh[37121]: time="2022-01-02T21:59:07.957626649+01:00" level=warning msg="Unable to find cpuset controller"
Jan 02 21:59:07 sk-Laptop dockerd-rootless.sh[37121]: time="2022-01-02T21:59:07.957716164+01:00" level=info msg="Loading containers: start."
Jan 02 21:59:08 sk-Laptop dockerd-rootless.sh[37121]: time="2022-01-02T21:59:08.007912512+01:00" level=info msg="Default bridge (docker0) is assigned with an IP address 172.17.0.0/16. D>
Jan 02 21:59:08 sk-Laptop dockerd-rootless.sh[37121]: time="2022-01-02T21:59:08.077361354+01:00" level=info msg="Loading containers: done."
Jan 02 21:59:08 sk-Laptop dockerd-rootless.sh[37121]: time="2022-01-02T21:59:08.080978248+01:00" level=warning msg="Not using native diff for overlay2, this may cause degraded performan>
Jan 02 21:59:08 sk-Laptop dockerd-rootless.sh[37121]: time="2022-01-02T21:59:08.081081192+01:00" level=info msg="Docker daemon" commit=459d0df graphdriver(s)=overlay2 version=20.10.12
Jan 02 21:59:08 sk-Laptop dockerd-rootless.sh[37121]: time="2022-01-02T21:59:08.081102319+01:00" level=info msg="Daemon has completed initialization"
Jan 02 21:59:08 sk-Laptop dockerd-rootless.sh[37121]: time="2022-01-02T21:59:08.091292835+01:00" level=info msg="API listen on /run/user/1000/docker.sock"
Jan 02 22:00:30 sk-Laptop dockerd-rootless.sh[37143]: time="2022-01-02T22:00:30.603612706+01:00" level=info msg="starting signal loop" namespace=moby path=/run/.ro995659387/user/1000/do>

sudo로 실행하면 systemctl"루트" 데몬이 활성화되지 않은 것으로 출력됩니다. 이는 정상적인 현상입니다.

$ sudo systemctl status docker
○ docker.service - Docker Application Container Engine
     Loaded: loaded (/lib/systemd/system/docker.service; disabled; vendor preset: enabled)
     Active: inactive (dead)
TriggeredBy: ○ docker.socket
       Docs: https://docs.docker.com

Jan 02 21:55:39 sk-Laptop dockerd[36685]: time="2022-01-02T21:55:39.318284987+01:00" level=info msg="Daemon has completed initialization"
Jan 02 21:55:39 sk-Laptop systemd[1]: Started Docker Application Container Engine.
Jan 02 21:55:39 sk-Laptop dockerd[36685]: time="2022-01-02T21:55:39.329132562+01:00" level=info msg="API listen on /run/docker.sock"
Jan 02 21:56:14 sk-Laptop systemd[1]: Stopping Docker Application Container Engine...
Jan 02 21:56:14 sk-Laptop dockerd[36685]: time="2022-01-02T21:56:14.005854836+01:00" level=info msg="Processing signal 'terminated'"
Jan 02 21:56:14 sk-Laptop dockerd[36685]: time="2022-01-02T21:56:14.006211665+01:00" level=info msg="stopping event stream following graceful shutdown" error="<nil>" module=l>
Jan 02 21:56:14 sk-Laptop dockerd[36685]: time="2022-01-02T21:56:14.006356148+01:00" level=info msg="Daemon shutdown complete"
Jan 02 21:56:14 sk-Laptop dockerd[36685]: time="2022-01-02T21:56:14.006382673+01:00" level=info msg="stopping event stream following graceful shutdown" error="context cancele>
Jan 02 21:56:14 sk-Laptop systemd[1]: docker.service: Deactivated successfully.
Jan 02 21:56:14 sk-Laptop systemd[1]: Stopped Docker Application Container Engine.

답변1

아래는이론, 그러나 테스트를 위해 루트 없는 모드로 전환할 수 있는 도커 호스트가 없습니다.

루트 없는 모드에서 실행할 때 docker 데몬이 수행할 수 있는 작업에는 몇 가지 제한 사항이 있습니다.

루트 없는 네트워킹을 어떻게 구현하는지 모르겠지만, 루트 없는 도커가 호스트의 네임스페이스에서 직접 공통 도커 인터페이스를 생성할 수 없다는 것은 이해가 됩니다. 일반 루트 모드에서 다음 명령을 입력하면 인터페이스를 볼 수 있습니다 ip address.

4: docker0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default 
    link/ether 02:42:88:1f:3d:89 brd ff:ff:ff:ff:ff:ff
    inet 172.17.0.1/16 brd 172.17.255.255 scope global docker0
       valid_lft forever preferred_lft forever
    inet6 fe80::42:88ff:fe1f:3d89/64 scope link 
       valid_lft forever preferred_lft forever

내 이론은 docker가 이것을 생성할 수 없다면 호스트와 통신할 수 없다는 것이 아니라 애플리케이션(postgresql)이 수신하지 않는다는 것이 문제라는 것입니다 172.17.0.1. 이는 루트 없는 모드의 문서화되지 않은 제한일 수 있습니다. 도커.

다행스럽게도 애플리케이션(postgresql)은 LAN 또는 WiFi IP 주소와 같은 다른 IP 주소를 계속 수신해야 합니다. Docker 컨테이너가 외부 세계(인터넷상의 모든 항목)에 액세스할 수 있는 경우 해당 IP의 호스트와 통신할 수 있어야 합니다.

ip address이 명령을 사용하여 로컬 IP 주소를 찾아 사용할 수 있습니다 .

관련 정보