Docker 컨테이너에서 대역폭 계산


13

Docker 컨테이너에서 오는 대역폭을 추적하는 방법을 찾으려고합니다.

일반적으로 --uid-owner특정 사용자의 대역폭 사용량을 추적하기 위해 마크로 사용합니다. 그러나 도커 컨테이너 내부의 사용자 --uid-owner가 작동하지 않으므로 모든 프로세스를 실행할 때도 마찬가지 입니다. 를 사용하는 대신도 --uid-owner커가 생성하는 가상 이더넷 장치에서 오는 모든 패킷을 추적하려고했습니다.

그러나 이것은 결국 아무것도하지 않았습니다. 내가 무엇을 시도하더라도 패킷이 잡히지 않습니다.

절박한 절망 속에서, 나는 모든 체인에 규칙을 적용하려고 시도했지만 결과도 없었습니다.

Chain PREROUTING (policy ACCEPT 3041 packets, 7849454 bytes)
num      pkts      bytes target     prot opt in     out     source               destination
1           0        0 MARK       tcp  --  veth5a36 any     anywhere             anywhere             MARK set 0x1

Chain INPUT (policy ACCEPT 273 packets, 23305 bytes)
num      pkts      bytes target     prot opt in     out     source               destination
1           0        0 MARK       tcp  --  veth5a36 any     anywhere             anywhere             MARK set 0x1

Chain FORWARD (policy ACCEPT 2750 packets, 7821109 bytes)
num      pkts      bytes target     prot opt in     out     source               destination
1           0        0 MARK       tcp  --  any    veth5a36  anywhere             anywhere             MARK set 0x1
2           0        0 MARK       tcp  --  veth5a36 any     anywhere             anywhere             MARK set 0x1
3           0        0            all  --  veth5a36 eth0    anywhere             anywhere             mark match 0x1

Chain OUTPUT (policy ACCEPT 293 packets, 80020 bytes)
num      pkts      bytes target     prot opt in     out     source               destination
1           0        0 MARK       tcp  --  any    veth5a36  anywhere             anywhere             MARK set 0x1

Chain POSTROUTING (policy ACCEPT 3043 packets, 7901129 bytes)
num      pkts      bytes target     prot opt in     out     source               destination
1           0        0 MARK       tcp  --  any    veth5a36  anywhere             anywhere             MARK set 0x1

도커 컨테이너에서 패키지를 성공적으로 표시하는 방법을 알려주는 사람이 있습니까? 바람직하게는 사용 --uid-owner하지만이 시점에서 나는 아무것도 취할 것입니다 :)

답변:


4

문제는 네임 스페이스와 관련이 있습니다. Docker는이를 사용하여 리소스를 격리합니다. 즉, 호스트의 총계에 포함되지 않습니다.

iptables호스트에서 실행할 때는 기본적으로 호스트의 네임 스페이스 만 살펴보고 관심있는 패킷이 컨테이너의 네임 스페이스에 맞춰집니다. 이 문제를 해결하려면 ip netns호스트에서 컨테이너의 네트워크 네임 스페이스에서 여전히 iptables를 실행 하는 데 사용할 수 있습니다 .

첫째, ip netns다소 직관적 인 인터페이스가 있습니다. 기존 프로세스 (이 경우 컨테이너) /var/run/netns/의 네임 스페이스에 연결 하려면 프로세스의 네임 스페이스 에 대한 링크를 만들어야 합니다.

# ln -sf /proc/`docker inspect -f '{{ .State.Pid }}' YOUR_CONTAINER`/ns/net /var/run/netns/SOME_NAME

(해야 할 수도 있습니다 mkdir /var/run/netns)

이제 컨테이너의 네임 스페이스에서 iptables를 자유롭게 실행할 수 있습니다.

# ip netns exec SOME_NAME iptables -L -nv

컨테이너 내부에 iptables의 규칙 세트가 출력되며, 아마도 비어있을 것입니다.

현재 --uid-owner를 사용하여 사용자 당 카운터를 보유하고 있다면 더 이상 필요하지 않습니다.이 경우 체인 카운터는 컨테이너에만 적용되고 충분하기 때문입니다.

마지막으로 정리할 수 있습니다 /var/run/netns.

사용자 당 여러 컨테이너

사용자 당 여러 컨테이너가 있고 함께 집계하려는 경우 컨테이너를로 시작하여 --net=container:OTHER_CONTAINER_FROM_USER네임 스페이스가 병합되도록 할 수 있습니다 .

이것은 열린 포트를 포함하여 네트워크 스택의 모든 측면을 병합하는 단점이 있으므로 동일한 포트에서 동일한 사용자가 청취하는 두 개의 컨테이너를 가질 수 없습니다.

이것이 매우 제한적인 경우 컨테이너를 개별적으로 집계하고 나중에 uid를 기준으로 그룹화 할 수 있습니다.

이 문제에 대한 자세한 내용은 여기를 참조하십시오 .


0

정확히 당신이 요구 한 것은 아니지만, 나는 그것이 일을 끝낼 것이라고 생각합니다.

Docker 블로그 에서 인용하십시오 .

인터페이스 레벨 카운터

각 컨테이너에는 가상 이더넷 인터페이스가 있으므로이 인터페이스의 TX 및 RX 카운터를 직접 확인할 수 있습니다.

[...]

그러나 현재로서는 가장 좋은 방법은 컨테이너 내에서 메트릭을 확인하는 것입니다. 컨테이너에서 특수 에이전트를 실행하는 것에 대해 말하는 것이 아닙니다. 호스트 환경에서 실행 파일을 실행하지만 컨테이너의 네트워크 네임 스페이스 내에서 실행합니다.

명령의 정확한 형식은 다음과 같습니다.

ip netns exec <nsname> <command...>

예를 들어 :

ip netns exec mycontainer netstat -i


2
귀하의 답변을 심하게 재 형식화했으며 향후 답변에서 유사한 스타일로 리소스를 인용하여 더 유용하게 사용하십시오.
fuero
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.