cron이랑 스크립트 몇 개가 /probe?host=NAME으로 POST하는 작은 내부 서비스 hostprobe를 만들고 있어요. 워커 4개, 큐 8, probe는 일단 20초 sleep이에요 (ssh 체크는 나중에 넣을 거예요). 스크립트가 폭주해도 서비스가 작게 유지되면 좋겠어요.
테스트로 hey -n 100 -c 100을 날렸어요. 100개 전부 몇 ms 만에 202로 돌아왔어요. 9번째부터는 느려지거나 거절될 거라고 예상했는데요. /stats는 queue len=8 cap=8에 4개 실행 중이라고 나와서, 채널이랑 워커는 맞게 동작하는 것 같아요. 그런데 runtime.NumGoroutine()이 100 정도고, /debug/pprof/goroutine?debug=1을 보면 같은 지점에 큰 그룹 하나가 멈춰 있어요. 요청을 1000개 보내면 큐는 8인 채로 goroutine이 1000 정도까지 올라갔어요. 활성 상태 보기 메모리도 버스트할 때마다 조금씩 올라가요.
핸들러랑 풀을 한동안 안 건드려서, 사실상 잊어버린 코드를 멍하니 보고 있어요. 핸들러예요:
job := Job{Host: host, Enqueued: time.Now()}
go func() {
q.jobs <- job
}()
atomic.AddInt64(&q.accepted, 1)
w.WriteHeader(http.StatusAccepted)
fmt.Fprintf(w, "queued %s\n", host)
풀은 흔한 for job := range q.jobs를 goroutine 4개에서 돌리는 거고, 채널은 make(chan Job, cfg.QueueDepth)예요.
늘어나는 goroutine은 어디서 오는 걸까요? 워커나 채널이 의심스러운데, 숫자상으로는 둘 다 멀쩡해요.
영어에서 번역·원문 보기I'm building hostprobe, a small internal service that cron and a few scripts POST to as /probe?host=NAME. Four workers, queue of 8, and the probe is a 20s sleep for now (the ssh check comes later). I want it to stay small when a script goes wild.
Test: hey -n 100 -c 100 against it. All 100 came back 202 in a few ms. I expected the 9th onward to be slowed or rejected. /stats says queue len=8 cap=8 and 4 running, so the channel and workers look right. But runtime.NumGoroutine() is about 100, and /debug/pprof/goroutine?debug=1 shows one big group sitting at the same spot. With 1000 requests it went to about 1000 while the queue stayed at 8. Activity Monitor memory also climbs a bit with each burst.
I haven't touched the handler or pool in a while, so I'm basically staring at code I forgot. Handler:
job := Job{Host: host, Enqueued: time.Now()}
go func() {
q.jobs <- job
}()
atomic.AddInt64(&q.accepted, 1)
w.WriteHeader(http.StatusAccepted)
fmt.Fprintf(w, "queued %s\n", host)
The pool is the usual for job := range q.jobs in 4 goroutines, and make(chan Job, cfg.QueueDepth).
Where are the extra goroutines coming from? I suspect the workers or the channel, but the counts say both are fine.