From: Timo Furrer Date: Wed, 28 Feb 2024 06:07:16 +0000 (+0000) Subject: net/http: add Request.CookiesNamed X-Git-Tag: go1.23rc1~824 X-Git-Url: http://www.git.cypherpunks.su/?a=commitdiff_plain;h=6dca7076560c8b34b536665296f03b748834c071;p=gostls13.git net/http: add Request.CookiesNamed Implements a new method http.Request.CookiesName, that allows retrieving all cookies that match the given name. Fixes #61472 Change-Id: I405d8771b4195af9ff6b4dfde3cfcd316c23b70c GitHub-Last-Rev: 6ad0094995b45648ebbcd18626f07bb879a3f7cf GitHub-Pull-Request: golang/go#61473 Reviewed-on: https://go-review.googlesource.com/c/go/+/511516 Reviewed-by: Emmanuel Odeke LUCI-TryBot-Result: Go LUCI Reviewed-by: Carlos Amedee Reviewed-by: Damien Neil --- diff --git a/api/next/61472.txt b/api/next/61472.txt new file mode 100644 index 0000000000..2e39c4b193 --- /dev/null +++ b/api/next/61472.txt @@ -0,0 +1 @@ +pkg net/http, method (*Request) CookiesNamed(string) []*Cookie #61472 diff --git a/src/net/http/request.go b/src/net/http/request.go index 99fdebcf9b..345ba3d4eb 100644 --- a/src/net/http/request.go +++ b/src/net/http/request.go @@ -431,6 +431,15 @@ func (r *Request) Cookies() []*Cookie { return readCookies(r.Header, "") } +// CookiesNamed parses and returns the named HTTP cookies sent with the request +// or an empty slice if none matched. +func (r *Request) CookiesNamed(name string) []*Cookie { + if name == "" { + return []*Cookie{} + } + return readCookies(r.Header, name) +} + // ErrNoCookie is returned by Request's Cookie method when a cookie is not found. var ErrNoCookie = errors.New("http: named cookie not present") diff --git a/src/net/http/request_test.go b/src/net/http/request_test.go index 6ce32332e7..8c8116123c 100644 --- a/src/net/http/request_test.go +++ b/src/net/http/request_test.go @@ -10,6 +10,7 @@ import ( "context" "crypto/rand" "encoding/base64" + "encoding/json" "errors" "fmt" "io" @@ -1256,6 +1257,76 @@ func TestRequestCookie(t *testing.T) { } } +func TestRequestCookiesByName(t *testing.T) { + tests := []struct { + in []*Cookie + filter string + want []*Cookie + }{ + { + in: []*Cookie{ + {Name: "foo", Value: "foo-1"}, + {Name: "bar", Value: "bar"}, + }, + filter: "foo", + want: []*Cookie{{Name: "foo", Value: "foo-1"}}, + }, + { + in: []*Cookie{ + {Name: "foo", Value: "foo-1"}, + {Name: "foo", Value: "foo-2"}, + {Name: "bar", Value: "bar"}, + }, + filter: "foo", + want: []*Cookie{ + {Name: "foo", Value: "foo-1"}, + {Name: "foo", Value: "foo-2"}, + }, + }, + { + in: []*Cookie{ + {Name: "bar", Value: "bar"}, + }, + filter: "foo", + want: []*Cookie{}, + }, + { + in: []*Cookie{ + {Name: "bar", Value: "bar"}, + }, + filter: "", + want: []*Cookie{}, + }, + { + in: []*Cookie{}, + filter: "foo", + want: []*Cookie{}, + }, + } + + for _, tt := range tests { + t.Run(tt.filter, func(t *testing.T) { + req, err := NewRequest("GET", "http://example.com/", nil) + if err != nil { + t.Fatal(err) + } + for _, c := range tt.in { + req.AddCookie(c) + } + + got := req.CookiesNamed(tt.filter) + + if !reflect.DeepEqual(got, tt.want) { + asStr := func(v any) string { + blob, _ := json.MarshalIndent(v, "", " ") + return string(blob) + } + t.Fatalf("Result mismatch\n\tGot: %s\n\tWant: %s", asStr(got), asStr(tt.want)) + } + }) + } +} + const ( fileaContents = "This is a test file." filebContents = "Another test file."