After some more testing, I found no confirmation for the hypothesis below.
In testing, I instrumented Go pluginserver with the pprof library, as follows:
import (
...
_ "net/http/pprof"
)
func main() {
go func() {
log.Println(http.ListenAndServe("localhost:6060", nil))
}()
...
}
Subsequently, observed the memory consumption behavior with
$ go tool pprof -top http://localhost:6060/debug/pprof/heap | head
Which shows:
Showing nodes accounting for 1028.13kB, 100% of 1028.13kB total
No significant increase was observed over time -- ran th tests for about 30 minutes.
I also modified the Go PDK server code to dump all instances in use at a given time, periodically -- patch here[1] if the 'how' is of interest.
That is, I get a list of all running instances periodically. If the instance leak was indeed happening, we would see that list grow indefinitely. Instead, what we see is the expected behavior of two total instances -- one for each worker (2 in my case):
2025/01/25 19:19:23 [info] 77663#0: *651 [go-hello:77667] 2025/01/25 19:19:23 INSTANCES, context: ngx.timer
2025/01/25 19:19:23 [info] 77663#0: *651 [go-hello:77667] GO: INSTANCE ID = 603, context: ngx.timer
2025/01/25 19:19:23 [info] 77663#0: *651 [go-hello:77667] GO: INSTANCE ID = 604, context: ngx.timer
2025/01/25 19:19:25 [info] 77663#0: *651 [go-hello:77667] 2025/01/25 19:19:25 INSTANCES, context: ngx.timer
2025/01/25 19:19:25 [info] 77663#0: *651 [go-hello:77667] GO: INSTANCE ID = 603, context: ngx.timer
2025/01/25 19:19:25 [info] 77663#0: *651 [go-hello:77667] GO: INSTANCE ID = 604, context: ngx.timer
2025/01/25 19:19:28 [info] 77663#0: *651 [go-hello:77667] 2025/01/25 19:19:28 INSTANCES, context: ngx.timer
2025/01/25 19:19:28 [info] 77663#0: *651 [go-hello:77667] GO: INSTANCE ID = 603, context: ngx.timer
2025/01/25 19:19:28 [info] 77663#0: *651 [go-hello:77667] GO: INSTANCE ID = 604, context: ngx.timer
2025/01/25 19:19:30 [info] 77663#0: *651 [go-hello:77667] 2025/01/25 19:19:30 INSTANCES, context: ngx.timer
2025/01/25 19:19:30 [info] 77663#0: *651 [go-hello:77667] GO: INSTANCE ID = 603, context: ngx.timer
2025/01/25 19:19:30 [info] 77663#0: *651 [go-hello:77667] GO: INSTANCE ID = 604, context: ngx.timer
2025/01/25 19:19:33 [info] 77663#0: *651 [go-hello:77667] 2025/01/25 19:19:33 INSTANCES, context: ngx.timer
2025/01/25 19:19:33 [info] 77663#0: *651 [go-hello:77667] GO: INSTANCE ID = 603, context: ngx.timer
2025/01/25 19:19:33 [info] 77663#0: *651 [go-hello:77667] GO: INSTANCE ID = 604, context: ngx.timer
On the Kong side, I start a simple configuration with a Go plugin enabled, start a loop with calls to and another loop with calls to while true; do http post :8001/config config=@~/Code/issues/go-pdk/go-pdk-210/kong.yml; done – effectively, causing the plugin iterator to be rebuilt repeatedly and new instances to be requested.
[1] https://gist.github.com/gszr/fefa5b7e3e7b334921616bdb2e668b77