사용자 지정 네트워크 보안 그룹이 트래픽을 차단합니다.
AKS(Azure Kubernetes Service) 클러스터에서 호스트되는 애플리케이션에 액세스하면 "시간 초과" 오류 메시지가 표시됩니다. 이 오류는 애플리케이션이 실행 중이고 나머지 구성이 올바른 것처럼 보이는 경우에도 발생할 수 있습니다.
필수 조건
Kubernetes kubectl 도구 또는 유사한 도구를 사용하여 클러스터에 연결합니다. Azure CLI를 사용하여 kubectl을 설치하려면 az aks install-cli 명령을 실행합니다.
클라이언트 URL(cURL) 도구 또는 유사한 명령줄 도구입니다.
패키지를 처리하기 위한 apt-get 명령줄 도구입니다.
증상
다음 kubectl get 및 cURL 명령을 실행하면 다음 콘솔 출력과 유사한 "시간 초과" 오류가 발생합니다.
$ kubectl get pods
NAME READY STATUS RESTARTS AGE
my-deployment-66648877fc-v78jm 1/1 Running 0 5m53s
$ kubectl get service
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
my-loadbalancer-service LoadBalancer 10.0.107.79 10.81.x.x 80:31048/TCP 4m14s
$ curl -Iv http://10.81.124.39 # Use an IP address that fits the "EXTERNAL-IP" pattern.
* Trying 10.81.x.x:80...
* connect to 10.81.x.x port 80 failed: Timed out
* Failed to connect to 10.81.x.x port 80 after 21033 ms: Timed out
* Closing connection 0
curl: (28) Failed to connect to 10.81.x.x port 80 after 21033 ms: Timed out
원인
매번 동일한 "시간 초과" 오류가 발생하는 경우 일반적으로 네트워크 구성 요소가 트래픽을 차단하고 있음을 시사합니다.
이 문제를 해결하려면 먼저 Pod에 대한 액세스를 확인한 다음 내부 아웃 방식으로 클라이언트로 이동할 수 있습니다.
Pod를 확인하려면 다음 kubectl get
을 실행하고 kubectl describe 명령을 실행합니다.
$ kubectl get pods -o wide
NAME READY STATUS RESTARTS AGE IP NODE
my-deployment-66648877fc-v78jm 1/1 Running 0 53s 172.25.0.93 aks-agentpool-42617579-vmss000000
$ kubectl describe pod my-deployment-66648877fc-v78jm # Specify the pod name from the previous command.
...
...
Events:
Type Reason Age From Message
---- ------ ---- ---- -------
Normal Scheduled 117s default-scheduler Successfully assigned default/my-deployment-66648877fc-v78jm to aks-agentpool-42617579-vmss000000
Normal Pulling 116s kubelet Pulling image "httpd"
Normal Pulled 116s kubelet Successfully pulled image "httpd" in 183.532816ms
Normal Created 116s kubelet Created container webserver
Normal Started 116s kubelet Started container webserver
이 출력에 따라 Pod가 다시 시작하지 않고 올바르게 실행되는 것 같습니다.
테스트 Pod를 열어 애플리케이션 Pod에 대한 액세스를 확인합니다. 다음kubectl get
, kubectl 실행 및 cURL 명령을 실행apt-get
합니다.
$ kubectl get pods -o wide # Get the pod IP address.
NAME READY STATUS RESTARTS AGE IP NODE
my-deployment-66648877fc-v78jm 1/1 Running 0 7m45s 172.25.0.93 aks-agentpool-42617579-vmss000000
$ kubectl run -it --rm aks-ssh --image=debian:stable # Launch the test pod.
If you don't see a command prompt, try pressing enter.
$ root@aks-ssh:
$ # Install packages inside the test pod.
$ root@aks-ssh: apt-get update -y && apt-get install dnsutils -y && apt-get install curl -y
Get:1 http://deb.debian.org/debian bullseye InRelease [116 kB]
Get:2 http://deb.debian.org/debian bullseye-updates InRelease [39.4 kB]
...
...
Running hooks in /etc/ca-certificates/update.d...
done.
$ # Try to check access to the pod using the pod IP address from the "kubectl get" output.
$ curl -Iv http://172.25.0.93
* Trying 172.25.0.93:80...
* Connected to 172.25.0.93 (172.25.0.93) port 80 (#0)
...
...
< HTTP/1.1 200 OK
HTTP/1.1 200 OK
...
...
* Connection #0 to host 172.25.0.93 left intact
Pod에 직접 액세스할 수 있습니다. 따라서 애플리케이션이 실행 중입니다.
정의된 서비스가 형식입니다 LoadBalancer
. 즉, 최종 클라이언트에서 Pod로의 요청 흐름은 다음과 같습니다.
클라이언트 >> 부하 분산 장치 >> AKS 노드 >> 애플리케이션 Pod
이 요청 흐름에서는 다음 구성 요소를 통해 트래픽을 차단할 수 있습니다.
- 클러스터의 네트워크 정책
- AKS 서브넷 및 AKS 노드에 대한 NSG(네트워크 보안 그룹)
네트워크 정책을 확인하려면 다음 명령을 실행합니다 kubectl get
.
$ kubectl get networkpolicy --all-namespaces
NAMESPACE NAME POD-SELECTOR AGE
kube-system konnectivity-agent app=konnectivity-agent 3h8m
AKS 기본 정책만 존재합니다. 따라서 네트워크 정책이 트래픽을 차단하지 않는 것 같습니다.
AKS를 사용하여 NSG 및 관련 규칙을 확인하려면 다음 단계를 수행합니다.
Azure Portal에서 가상 머신 확장 집합을 검색하고 선택합니다.
확장 집합 인스턴스 목록에서 사용 중인 인스턴스를 선택합니다.
확장 집합 인스턴스의 메뉴 창에서 .를 선택합니다
Networking
.
확장 집합 인스턴스에 대한 네트워킹 페이지가 나타납니다. 인바운드 포트 규칙 탭에는 확장 집합 인스턴스에서 작동하는 두 NSG를 기반으로 하는 두 개의 규칙 집합이 표시됩니다.
첫 번째 집합은 서브넷 수준에서 NSG 규칙으로 구성됩니다. 이러한 규칙은 다음 참고 제목 아래에 표시됩니다.
네트워크 보안 그룹 my-aks-nsg>(서브넷에 연결됨:< my-aks-subnet>)<
이 정렬은 AKS 클러스터에 대한 사용자 지정 가상 네트워크 및 사용자 지정 서브넷을 사용하는 경우에 일반적입니다. 서브넷 수준의 규칙 집합은 다음 표와 유사할 수 있습니다.
우선 순위 Name 포트 프로토콜 원본 대상 작업 65000 AllowVnetInBound 모두 모두 VirtualNetwork VirtualNetwork 허용 65001 AllowAzureLoadBalancerInBound 모두 모두 AzureLoadBalancer 모두 허용 65500 DenyAllInBound 모두 모두 모두 모두 거부 두 번째 집합은 네트워크 어댑터 수준의 NSG 규칙으로 구성됩니다. 이러한 규칙은 다음 참고 제목 아래에 표시됩니다.
네트워크 보안 그룹 aks-agentpool-agentpool-number-nsg<>(네트워크 인터페이스에 연결됨: aks-agentpool-vm-scale-set-number-vmss)<>
이 NSG는 AKS 클러스터에 의해 적용되며 AKS에서 관리됩니다. 해당 규칙 집합은 다음 표와 유사할 수 있습니다.
우선 순위 Name 포트 프로토콜 원본 대상 작업 500 <guid-TCP-80-Internet> 80 TCP 인터넷 10.81.x.x 허용 65000 AllowVnetInBound 모두 모두 VirtualNetwork VirtualNetwork 허용 65001 AllowAzureLoadBalancerInBound 모두 모두 AzureLoadBalancer 모두 허용 65500 DenyAllInBound 모두 모두 모두 모두 거부
네트워크 어댑터 수준에서는 IP 주소 10.81에서 TCP에 대한 NSG 인바운드 규칙이 있습니다.x.포트 80의 x (표에 강조 표시됨). 그러나 서브넷 수준의 NSG에 대한 규칙에서 동등한 규칙이 누락되었습니다.
AKS가 사용자 지정 NSG에 규칙을 적용하지 않은 이유는 무엇인가요? AKS는 서브넷에 NSG를 적용하지 않으므로 해당 서브넷과 연결된 NSG는 수정되지 않습니다. AKS는 네트워크 어댑터 수준에서만 NSG를 수정합니다. 자세한 내용은 AKS를 사용하여 NSG를 구성할 수 있나요?를 참조하세요.
솔루션
애플리케이션이 특정 포트에 액세스할 수 있도록 설정된 경우 사용자 지정 NSG에서 해당 포트를 규칙으로 Inbound
허용하는지 확인해야 합니다. 서브넷 수준의 사용자 지정 NSG에 적절한 규칙이 추가되면 애플리케이션에 액세스할 수 있습니다.
$ curl -Iv http://10.81.x.x
* Trying 10.81.x.x:80...
* Connected to 10.81.x.x (10.81.x.x) port 80 (#0)
...
...
< HTTP/1.1 200 OK
HTTP/1.1 200 OK
...
...
* Connection #0 to host 10.81.x.x left intact
도움을 요청하십시오.
질문이 있거나 도움이 필요한 경우 지원 요청을 생성하거나Azure 커뮤니티 지원에 문의하세요. Azure 피드백 커뮤니티에 제품 피드백을 제출할 수도 있습니다.