{"id":"IL-0056","org":"MindTickle","date":"2020-03-16","docs":["https://docs.aws.amazon.com/eks/latest/userguide/external-snat.html","https://tech.xing.com/a-reason-for-unexplained-connection-timeouts-on-kubernetes-docker-abd041cf7e02","https://github.com/awsdocs/amazon-eks-user-guide/pull/53"],"title":{"en":"Calls from EKS pods to services behind an NLB in another VPC failed intermittently because the AWS VPC CNI did source NAT on the node","ko":"kops 에서 EKS 로 옮긴 뒤 AWS VPC CNI 의 SNAT 때문에 파드에서 다른 VPC 의 NLB 뒤 서비스로 가는 호출이 간헐적으로 실패했다"},"domain":["kubernetes","aws","networking"],"impact":{"scope":"production platform slow and unstable after the switch to EKS; calls from pods to services behind NLBs in another VPC failed intermittently","users":"unknown","region":"unknown"},"review":{"written_by":"session","reviewed_at":null,"reviewed_by":null},"lessons":{"en":"In a networking problem every component in the stack is a suspect; ruling out EKS early cost a lot of time. A DaemonSet that pinged every component from every other one exposed the anomaly that led to the fix. The team had only skimmed the AWS CNI documentation before the migration; knowing how the plugin works internally would have led to better judgements and hypotheses while debugging.","ko":"장애를 디버깅할 때, 특히 네트워크 문제라면 스택 전체의 구성 요소를 모두 의심해야 한다. EKS 를 원인 후보에서 일찍 뺀 탓에 귀중한 시간을 많이 잃었다. 관측 도구를 작업 흐름에 넣어야 한다. 모든 구성 요소가 서로 핑을 보내는 pinger DaemonSet 으로 이상한 연결 현상을 보고 나서야 해결에 다가갈 수 있었다. 쓰는 시스템을 알아야 한다. 팀은 EKS 로 옮기기 전에 AWS CNI 문서를 훑어보기만 하고 구현을 제대로 살피지 않았다. 내부 동작을 알았다면 디버깅 방법과 가설을 더 잘 세웠을 것이다."},"related":[],"sources":[{"url":"https://yashmehrotra.com/posts/the-case-of-the-missing-packet-an-eks-migration-tale/","kind":"blog","license":"unknown","archived":null}],"summary":{"en":"The team planned to move its production cluster from kops to EKS on the first weekend after New Year's, the lowest-traffic period for the platform. One of the reasons for EKS was networking, because Weave had caused a lot of trouble on the kops cluster. A new production cluster had been set up and the production apps migrated onto it. After the switch the platform became slow and unstable and the team reverted. A support case with AWS went to a networking expert.\n\nAbout a month of packet captures followed. Traffic inside the cluster was fine, but calls from pods to services on EC2 behind NLBs failed intermittently, and the reachability from pods and nodes did not make sense. At the end of a call, AWS suggested setting AWS_VPC_K8S_CNI_EXTERNALSNAT=true. With that setting the calls worked as expected.\n\nThe AWS VPC CNI gives each pod its own VPC IP address using secondary addresses on the instance. Traffic within a VPC goes directly between private addresses without source network address translation (SNAT). For a destination outside the VPC, the plugin rewrites the pod's address to the primary private IP of the node's primary network interface. The NLBs were in a different VPC, so the SNAT happened on the node. The author's explanation is that the plugin translated the pod's address towards an internet gateway, and with no internet gateway in that path the traffic broke. With external SNAT enabled, the plugin does no translation and the NAT gateway translates traffic from the pod to the internet. After the change the cluster had no further networking problems, and all traffic was moved onto EKS.","ko":"운영 클러스터를 kops 에서 EKS 로 옮기다 겪은 장애를 팀의 엔지니어가 정리한 글이다. 팀은 weave 네트워킹 때문에 문제를 많이 겪었고, 네트워킹이 나아지는 것이 EKS 로 옮기는 큰 이유였다. 트래픽이 가장 적은 새해 첫 주말에 옮겼지만 플랫폼이 매우 느리고 불안정해져 되돌렸다. 팀은 AWS 지원팀에 EKS 문제로 지원 케이스를 열었고, 케이스는 네트워크 전문가에게 넘어갔다.\n\n패킷 캡처로 클러스터 안의 호출은 정상이고, NLB 뒤 EC2 머신으로 가는 호출만 간헐적으로 실패한다는 것을 알았다. 노드와 EC2 서버 사이에는 패킷 재전송이 많았다. AWS 네트워크 전문가는 EC2 서버 설정을 의심했고, 팀은 한 달 동안 트래픽을 만들고 tcpdump 를 떠서 보냈다. 글쓴이가 파드와 노드에서 서버로 가는 연결이 엇갈려 성공하고 실패하는 현상을 찾았고, 그 뒤 AWS 쿠버네티스 전문가가 함께하는 통화를 잡았다. 그 사이에는 큰 문제가 없던 ELB 를 임시로 쓰기로 했다. 통화가 끝날 무렵 AWS 쪽이 AWS_VPC_K8S_CNI_EXTERNALSNAT=true 설정을 제안했고, 이 설정을 켜자 모든 것이 원래 기대한 대로 동작했다.\n\nAWS CNI 플러그인은 노드에 VPC IP 주소를 할당하고, 인스턴스에 보조 IP 주소를 만들어 파드마다 클러스터 밖에서 직접 닿을 수 있는 자기 IP 를 준다. SNAT 은 패킷의 출발지 주소를 바꾸는 주소 변환이다. VPC 안의 통신은 사설 IP 끼리 직접 오가므로 SNAT 이 필요 없다. 목적지가 VPC 밖이면 CNI 플러그인은 파드의 사설 IP 를 노드의 기본 사설 IP 로 바꾼다. 이 주소는 그 파드가 도는 노드의 기본 네트워크 인터페이스에 할당된 주소다. NLB 가 다른 VPC 에 있었으므로 노드에서 CNI 플러그인이 SNAT 을 했다. 글에 따르면 CNI 플러그인은 파드 IP 를 인터넷 게이트웨이의 IP 로 바꾸었는데, 인터넷 게이트웨이가 없어 통신이 깨졌다. 외부 SNAT 을 켜면 CNI 플러그인은 주소를 변환하지 않고, 파드에서 인터넷으로 가는 트래픽은 NAT 게이트웨이가 변환한다. 이후 클러스터에는 네트워크 문제가 없었고, 팀은 모든 트래픽을 EKS 로 옮겼다. 이 일은 한 달 반 동안 이어졌다."},"trigger":{"en":"Production was moved from a kops cluster using Weave networking to a new EKS cluster using the AWS VPC CNI, without external SNAT enabled.","ko":"운영 클러스터를 kops 에서 EKS 로 옮겼고, AWS VPC CNI 가 다른 VPC 에 있는 NLB 로 가는 파드 트래픽의 출발지 주소를 노드에서 변환했다."},"severity":"unknown","symptoms":["intermittent-connection-failures","high-latency"],"timeline":{"detected_after":null,"resolved_after":null},"date_kind":"published","detection":{"en":"The team lead saw the platform behaving very slowly after the switch to EKS and phoned the author.","ko":"EKS 로 옮긴 날 팀이 플랫폼이 매우 느리게 동작하는 것을 보았다. 실패하는 호출의 패턴은 AWS 네트워크 전문가가 요청한 패킷 캡처를 하고 나서야 보였다."},"components":["vpc-cni"],"root_cause":"dns-network","remediation":[{"text":{"en":"reverted production to the kops cluster","ko":"플랫폼이 너무 불안정해 운영을 이어 갈 수 없었으므로 EKS 이전을 되돌렸다."}},{"text":{"en":"set AWS_VPC_K8S_CNI_EXTERNALSNAT=true in the AWS VPC CNI","ko":"AWS VPC CNI 에 AWS_VPC_K8S_CNI_EXTERNALSNAT=true 를 설정해 외부 SNAT 을 켰다. 이제 CNI 플러그인은 주소를 변환하지 않고 NAT 게이트웨이가 변환한다."}}],"action_items":[{"text":{"en":"Monitor and alert on the AWS VPC CNI","ko":"AWS CNI 에 모니터링과 경보를 설정했다."}}],"contributing":["default-config-unchanged","assumption-unverified"],"recurrence_of":null,"symptoms_text":{"en":"On the Saturday the production cluster was moved from kops to EKS, the platform became very slow and too unstable to keep running, and the team reverted.\n\nPacket captures requested by an AWS Support networking expert showed the pattern. Network calls inside the cluster worked. Calls from pods to microservices on EC2 machines behind an NLB (Network Load Balancer) failed intermittently. Captures taken on the sending pods, on their Kubernetes nodes and on the receiving EC2 machines showed many packet retransmissions between the node and the EC2 server.\n\nThe AWS expert read the captures as a misconfiguration on the EC2 servers and asked for socket and network statistics along with the tcpdumps. Generating traffic and collecting captures went on for a month. Then connection-check scripts showed a crossed pattern: a status endpoint was reachable from Pod-A on Node-A but not from Node-A itself, while it was reachable from Node-B but not from Pod-B on Node-B.\n\nOn a call with AWS's Kubernetes experts, changes they suggested to the node's networking module broke networking on that node completely, so no tools could be installed to debug further. In the meantime the team used an ELB, which was not showing many problems.","ko":"새해 첫 주말, 운영 클러스터를 kops 에서 EKS 로 옮긴 날 아침에 팀장이 전화로 플랫폼이 매우 느리게 동작한다고 알렸다. 아직 패턴은 보이지 않았고, 너무 불안정해서 계속 운영할 수 없는 상태였다.\n\nAWS 지원팀의 네트워크 전문가가 패킷 캡처를 요청했고, 캡처를 하고서야 패턴이 보였다. 클러스터 안의 네트워크 호출은 모두 정상이었지만 클러스터 밖으로 나가는 호출이 실패했다. 팀은 AWS 의 네트워크 로드 밸런서인 NLB 뒤의 EC2 머신에서 마이크로서비스 몇 개를 돌렸는데, 이 서비스로 가는 호출이 모두 간헐적으로 실패했다. 요청을 보내는 파드, 그 파드가 도는 쿠버네티스 노드, 요청을 받는 EC2 머신에서 패킷을 캡처하자 쿠버네티스 노드와 EC2 서버 사이에 패킷 재전송이 많이 보였다.\n\n글쓴이는 파드마다 자기 사설 IP 를 주는 AWS CNI 를 의심했다. 같은 구성이 kops 클러스터에서는 잘 동작했기 때문이다. 하지만 AWS 네트워크 전문가는 패킷 캡처가 서버 설정 오류를 가리킨다고 보았고, EKS 가 아니라 EC2 머신의 설정이 잘못됐다고 확신했다. 팀은 tcpdump 와 함께 소켓 통계와 네트워크 통계를 모으고, 인위적으로 트래픽을 만들어 캡처를 떠서 보내는 일을 한 달 동안 되풀이했다.\n\n그러다 글쓴이가 만든 연결 확인 스크립트에서 이상한 현상이 보였다. Node-A 에서 도는 Pod-A 에서는 서버의 상태 엔드포인트에 닿았지만 Node-A 에서 직접 호출하면 닿지 않았다. 반대로 Node-B 에서는 서버에 닿았지만 Node-B 에서 도는 Pod-B 에서는 닿지 않았다. 이후 AWS 쿠버네티스 전문가와 통화하며 그가 요청한 대로 노드의 네트워크 모듈을 조정하다가 그 노드의 네트워크가 아예 끊겼다. 외부 인터넷에 닿지 못해 디버깅 도구도 설치할 수 없었다."},"updated_at":"2026-11-10T00:00:38.909089Z","url":"https://benchlet.com/incidentlib/app/cases/IL-0056","org_slug":"mindtickle"}