loopfz / gadgeto

Gadgeto! is a collection of tools that aim to facilitate the development of REST APIs in Go.

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

fatal error: concurrent map writes

rbeuque74 opened this issue · comments

When tonic is used inside unit tests, multiple gin instance can register routes at the same time, calling tonic/handler.go func Handler, which is not thread safe.

Example:

fatal error: concurrent map writes

goroutine 1 [running]:
runtime.throw(0xe06541, 0x15)
	/home/romain/go/src/runtime/panic.go:774 +0x72 fp=0xc0004fd848 sp=0xc0004fd818 pc=0x431412
runtime.mapassign_faststr(0xcdffc0, 0xc00030b920, 0xc0005f61e0, 0x49, 0xf8aa80)
	/home/romain/go/src/runtime/map_faststr.go:211 +0x417 fp=0xc0004fd8b0 sp=0xc0004fd848 pc=0x4150d7
github.com/loopfz/gadgeto/tonic.Handler(0xcd2940, 0xe34ef8, 0xc8, 0x0, 0x0, 0x0, 0x0)
	/home/romain/gopath/src/github.com/ovh/utask/vendor/github.com/loopfz/gadgeto/tonic/handler.go:132 +0x5cf fp=0xc0004fda70 sp=0xc0004fd8b0 pc=0xbb604f
github.com/ovh/utask/api.(*Server).build(0xc0001ac940, 0xf73c80, 0xc0000ca010)
	/home/romain/gopath/src/github.com/ovh/utask/api/server.go:312 +0x230e fp=0xc0004fdda8 sp=0xc0004fda70 pc=0xc0d1fe
github.com/ovh/utask/api.(*Server).Handler(...)
	/home/romain/gopath/src/github.com/ovh/utask/api/server.go:112
github.com/ovh/utask/api_test.TestMain(0xc0001c6380)
	/home/romain/gopath/src/github.com/ovh/utask/api/api_test.go:81 +0x37d fp=0xc0004fdef8 sp=0xc0004fdda8 pc=0xc17f7d
main.main()
	_testmain.go:58 +0x135 fp=0xc0004fdf60 sp=0xc0004fdef8 pc=0xc20995
runtime.main()
	/home/romain/go/src/runtime/proc.go:203 +0x21e fp=0xc0004fdfe0 sp=0xc0004fdf60 pc=0x432dae
runtime.goexit()
	/home/romain/go/src/runtime/asm_amd64.s:1357 +0x1 fp=0xc0004fdfe8 sp=0xc0004fdfe0 pc=0x461391

goroutine 5 [syscall]:
os/signal.signal_recv(0x461396)
	/home/romain/go/src/runtime/sigqueue.go:147 +0x9c
os/signal.loop()
	/home/romain/go/src/os/signal/signal_unix.go:23 +0x22
created by os/signal.init.0
	/home/romain/go/src/os/signal/signal_unix.go:29 +0x41

goroutine 41 [chan receive (nil chan)]:
github.com/ovh/utask/engine.Init.func2(0xf73c80, 0xc0000ca010)
	/home/romain/gopath/src/github.com/ovh/utask/engine/engine.go:95 +0x48
created by github.com/ovh/utask/engine.Init
	/home/romain/gopath/src/github.com/ovh/utask/engine/engine.go:94 +0x3bb

goroutine 30 [runnable]:
github.com/loopfz/gadgeto/tonic.Handler(0xceedc0, 0xe34f78, 0xc8, 0x0, 0x0, 0x0, 0x0)
	/home/romain/gopath/src/github.com/ovh/utask/vendor/github.com/loopfz/gadgeto/tonic/handler.go:132 +0x5cf
github.com/ovh/utask/api.(*Server).build(0xc0001ac940, 0xf73c40, 0xc0001acbc0)
	/home/romain/gopath/src/github.com/ovh/utask/api/server.go:184 +0xc09
github.com/ovh/utask/api.(*Server).ListenAndServe(0xc0001ac940, 0x0, 0x0)
	/home/romain/gopath/src/github.com/ovh/utask/api/server.go:89 +0x84
created by github.com/ovh/utask/api_test.TestMain
	/home/romain/gopath/src/github.com/ovh/utask/api/api_test.go:74 +0x271

func Handler is adding routes to a map, in order to be collected in tonic.go func GetRoutes
I guess that registering routes on different gin.Engine will register routes on the same map, and will probably create some inconsistency.

I will open a pull-request to fix the panic first, but I guess another bug fix should be open regarding the routes registering inconsistency.