mirror of
https://github.com/gin-gonic/gin.git
synced 2025-10-22 01:12:16 +08:00
Fix context.Params race condition on Copy()
Using context.Param(key) on a context.Copy inside a goroutine may lead to incorrect value on a high load, where another request overwrite a Param
This commit is contained in:
parent
2e915f4e50
commit
8709d894ef
@ -87,6 +87,9 @@ func (c *Context) Copy() *Context {
|
||||
for k, v := range c.Keys {
|
||||
cp.Keys[k] = v
|
||||
}
|
||||
paramCopy := make([]Param, len(cp.Params))
|
||||
copy(paramCopy, cp.Params)
|
||||
cp.Params = paramCopy
|
||||
return &cp
|
||||
}
|
||||
|
||||
|
@ -13,6 +13,7 @@ import (
|
||||
"mime/multipart"
|
||||
"net/http"
|
||||
"net/http/httptest"
|
||||
"os"
|
||||
"reflect"
|
||||
"strings"
|
||||
"testing"
|
||||
@ -1812,3 +1813,20 @@ func TestContextResetInHandler(t *testing.T) {
|
||||
c.Next()
|
||||
})
|
||||
}
|
||||
|
||||
func TestRaceParamsContextCopy(t *testing.T) {
|
||||
DefaultWriter = os.Stdout
|
||||
router := Default()
|
||||
nameGroup := router.Group("/:name")
|
||||
{
|
||||
nameGroup.GET("/api", func(c *Context) {
|
||||
go func(c *Context, param string) {
|
||||
time.Sleep(100 * time.Millisecond)
|
||||
assert.Equal(t, c.Param("name"), param)
|
||||
}(c.Copy(), c.Param("name"))
|
||||
})
|
||||
}
|
||||
performRequest(router, "GET", "/name1/api")
|
||||
performRequest(router, "GET", "/name2/api")
|
||||
time.Sleep(200 * time.Millisecond)
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user