Go 서비스가 timeout, goroutine 증가, 이상한 런타임 증상을 동시에 보일 때 가장 어려운 건 고치는 방법보다도 어디서부터 봐야 하는지를 정하는 일입니다.
처음 분기를 잘못 잡으면 timeout만 계속 조정하다가 실제 원인이 blocked work인 걸 놓칠 수 있고, goroutine leak만 의심하다가 사실은 database saturation이 주원인인 상황도 나옵니다. 이 허브 글은 그 첫 분기를 더 빨리 고르기 위해 만들었습니다.
이 글은 이 블로그의 Golang 트러블슈팅 허브입니다. 운영 상황에서 가장 눈에 띄는 증상부터 고르고, 그 증상과 가장 가까운 가이드로 먼저 들어가면 됩니다.
먼저 보이는 실패 패턴부터 나누기
처음엔 이런 질문으로 시작하면 좋습니다.
context deadline exceeded가 반복되는가- goroutine 수가 계속 올라가고 다시 내려오지 않는가
- 단순히 느린 것이 아니라 handler가 막혀 보이는가
- 트래픽이 줄어도 shutdown이 끝나지 않는가
- memory, pool, queue 쪽 압박이 먼저 보이는가
이 질문이 중요한 이유는 Go 장애가 겹쳐서 나타나는 경우가 많기 때문입니다. timeout, goroutine 증가, queueing이 한꺼번에 보일 수도 있습니다. 처음부터 장애 전체를 완벽히 분류하는 것이 목적이 아니라, 가장 정보량이 많은 첫 분기를 잡는 것이 목적입니다.
빠른 triage용 명령 예시
급하게 첫 상태를 볼 때는 이런 확인만으로도 다음 분기를 고르기 좋습니다.
curl http://localhost:6060/debug/pprof/goroutine?debug=1
curl http://localhost:6060/debug/pprof/heap
curl http://localhost:6060/debug/pprof/profile?seconds=20
첫 명령에서 완벽한 확신이 필요한 것은 아닙니다. timeout 예산 소진인지, concurrency blockage인지, runtime pressure인지 대략 나눌 수 있으면 충분합니다.
timeout budget 문제처럼 보일 때
다음 같은 패턴이면 Golang Context Deadline Exceeded부터 보세요.
- 요청이 부하에서 timeout 난다
- upstream 또는 database latency가 경로를 지배한다
- retry나 nested deadline이 의심된다
- outbound HTTP client timeout이 반복된다
핵심 질문이 “시간 예산이 어디서 사라졌는가”라면 이 글이 가장 좋은 출발점입니다.
blocked work 또는 concurrency drift처럼 보일 때
다음 같은 패턴이면 Golang Goroutine Leak부터 보세요.
- goroutine 수가 계속 늘고 원래 수준으로 돌아오지 않는다
- blocked channel이 의심된다
- cancellation이나 shutdown 경로가 불완전해 보인다
- background worker가 요청이나 job보다 오래 살아남는다
핵심 질문이 “어떤 작업이 걸려 있고 왜 빠져나오지 못하는가”라면 이 분기가 맞습니다.
더 구체적인 동시성 분기로는 아래 글이 이어집니다.
운영 압박이나 종료 경로 문제처럼 보일 때
런타임 압박, resource exhaustion, shutdown 문제처럼 보이면 아래 글들이 더 좋은 출발점입니다.
- Golang Memory Usage High
- Golang HTTP Server Shutdown Hangs
- Golang Database Connections Exhausted
- Golang Panic in Goroutine
timeout이나 goroutine보다 먼저 서비스 전체 건강 상태가 무너져 보일 때 특히 유용합니다.
간단한 Go 분기 지도
빠르게 나누면 이렇게 보면 됩니다.
- timeout budget, latency, retry, 느린 downstream 경계: deadline 글부터
- blocked worker, goroutine 증가, hanging channel, 불명확한 종료 경로: goroutine 글부터
- pool 고갈, memory 압박, shutdown hang, 런타임 불안정: 운영 압박 글부터
이 지도는 의도적으로 단순합니다. 장애 전체를 설명하는 것이 아니라, 가장 유용한 다음 페이지로 빨리 이동하기 위한 안내입니다.
증상이 여러 개 같이 보일 때
이 증상들이 같이 나타나는 것은 자연스럽습니다.
느린 dependency는 timeout 에러와 goroutine 증가를 함께 만들 수 있습니다. 막힌 worker pool은 queueing, memory 사용량 증가, shutdown 지연을 같이 만들 수 있습니다. database pool 병목은 애플리케이션 쪽에서는 timeout처럼 보이고 인프라 쪽에서는 resource exhaustion처럼 보일 수 있습니다.
이럴 때는 사용자에게 가장 직접적인 장애부터 시작하세요.
- 사용자가 보는 에러가 timeout이라면 deadline 글부터
- 걸린 작업과 goroutine 증가가 더 분명하다면 goroutine 글부터
- 서비스 전체가 압박받는 모습이 먼저라면 운영 압박 글부터
그리고 바로 인접 분기를 이어서 비교하면 됩니다. 목적은 장애를 억지로 한 상자에 넣는 것이 아니라, 증상에서 원인으로 가는 거리를 줄이는 것입니다.
FAQ
Q. 이 글은 Go 설정 가이드인가요?
아니요. 운영 장애에서 첫 분기를 고르기 위한 증상 기준 허브 글입니다.
Q. timeout과 goroutine 증가가 같이 보이면 어떻게 하나요?
사용자에게 더 직접적인 장애를 먼저 일으키는 증상부터 보고, 바로 다음 글에서 인접 분기를 비교하세요. 실제 운영에서는 두 경로가 자주 겹칩니다.
Q. 어떤 사람에게 가장 유용한가요?
기본 Go 문법은 이미 알고 있고, 장애 상황에서 다음 디버깅 분기를 더 빨리 고르고 싶은 엔지니어에게 특히 유용합니다.
Read Next
- timeout budget이 가장 눈에 띄면 Golang Context Deadline Exceeded로 가세요.
- blocked work와 goroutine 증가가 더 눈에 띄면 Golang Goroutine Leak으로 가세요.
- 서비스 전체 압박이 먼저 보이면 Golang Memory Usage High로 가세요.
Related Posts
- Golang Context Deadline Exceeded
- Golang Goroutine Leak
- Golang HTTP Client Timeout
- Golang Channel Deadlock
- Golang Memory Usage High
- Golang HTTP Server Shutdown Hangs
- Language category archive
심사 대기 중에는 광고 대신 관련 가이드를 먼저 보여줍니다.
먼저 읽어볼 가이드
검색 유입이 많은 핵심 글부터 이어서 보세요.
- 미들웨어 트러블슈팅 가이드: Redis vs RabbitMQ vs Kafka 개발자를 위한 미들웨어 트러블슈팅 허브 글입니다. Redis, RabbitMQ, Kafka 중 어떤 증상부터 먼저 봐야 하는지와 어떤 문제 패턴이 각 시스템에 가까운지 정리합니다.
- Kubernetes CrashLoopBackOff: 먼저 볼 것들 startup failure, probe, config, resource limit 관점에서 CrashLoopBackOff를 어떻게 나눠서 봐야 하는지 정리한 가이드입니다.
- Kafka consumer lag가 계속 늘 때: 트러블슈팅 가이드 Kafka consumer lag가 계속 늘어날 때 무엇부터 봐야 하는지 정리합니다. poll 주기, 처리 속도, rebalance, consumer 설정까지 실전 기준으로 다룹니다.
- Kafka Rebalancing Too Often 가이드 Kafka consumer group에서 rebalance가 너무 자주 일어날 때 membership flapping, poll timing, protocol, assignment churn을 어떤 순서로 봐야 하는지 설명하는 실전 가이드입니다.
- Docker container가 계속 재시작될 때: 먼저 확인할 것들 exit code, command failure, environment mistake, health check 관점에서 Docker restart loop를 푸는 실전 가이드입니다.
심사 대기 중에는 광고 대신 관련 가이드를 먼저 보여줍니다.