From 50b18c7515bc6eaaa659e63423379ceb5cacc4ff Mon Sep 17 00:00:00 2001 From: "Gerasimos (Makis) Maropoulos" Date: Sat, 9 May 2020 14:04:51 +0300 Subject: [PATCH] enhanced cookie security and management Former-commit-id: a97b0b33e87749a2e8c32e63269fcc60fa326ff3 --- HISTORY.md | 13 +- _examples/authentication/oauth2/main.go | 12 +- _examples/cookies/basic/main_test.go | 6 +- _examples/cookies/securecookie/main.go | 71 ++-- _examples/cookies/securecookie/main_test.go | 10 +- .../listen-addr-public/README.md | 1 - .../http-listening/listen-addr-public/main.go | 2 +- .../tunneling_screenshot.png | Bin 168290 -> 0 bytes .../read-json-struct-validation/main.go | 2 +- _examples/sessions/securecookie/main.go | 9 +- configuration.go | 2 +- context/context.go | 389 +++++++++++++----- iris.go | 64 +-- sessions/config.go | 61 +-- sessions/cookie.go | 142 ------- sessions/lifetime.go | 4 +- sessions/sessions.go | 121 +++--- sessions/sessions_test.go | 47 ++- 18 files changed, 490 insertions(+), 466 deletions(-) delete mode 100644 _examples/http-listening/listen-addr-public/README.md delete mode 100644 _examples/http-listening/listen-addr-public/tunneling_screenshot.png delete mode 100644 sessions/cookie.go diff --git a/HISTORY.md b/HISTORY.md index 2e69656a..5d0fba48 100644 --- a/HISTORY.md +++ b/HISTORY.md @@ -371,12 +371,13 @@ Other Improvements: ![DBUG routes](https://iris-go.com/images/v12.2.0-dbug2.png?v=0) +- Enhanced cookie security and management through new `Context.AddCookieOptions` method and new cookie options (look on New Package-level functions section below), [securecookie](https://github.com/kataras/iris/tree/master/_examples/cookies/securecookie) example has been updated. - `iris.TLS` can now accept certificates as raw contents too. - `iris.TLS` registers a secondary http server which redirects "http://" to their "https://" equivalent requests, unless the new `iris.TLSNoRedirect` host Configurator is provided on `iris.TLS` (or `iris.AutoTLS`), e.g. `app.Run(iris.TLS("127.0.0.1:443", "mycert.cert", "mykey.key", iris.TLSNoRedirect))`. - Fix an [issue](https://github.com/kataras/i18n/issues/1) about i18n loading from path which contains potential language code. -- Server will not return neither log the `ErrServerClosed` if `app.Shutdown` was called manually via interrupt signal(CTRL/CMD+C), note that if the server closed by any other reason the error will be fired as previously (unless `iris.WithoutServerError(iris.ErrServerClosed)`). +- Server will not return neither log the `ErrServerClosed` error if `app.Shutdown` was called manually via interrupt signal(CTRL/CMD+C), note that if the server closed by any other reason the error will be fired as previously (unless `iris.WithoutServerError(iris.ErrServerClosed)`). - Finally, Log level's and Route debug information colorization is respected across outputs. Previously if the application used more than one output destination (e.g. a file through `app.Logger().AddOutput`) the color support was automatically disabled from all, including the terminal one, this problem is fixed now. Developers can now see colors in their terminals while log files are kept with clear text. @@ -396,8 +397,16 @@ Other Improvements: - Fix [#1473](https://github.com/kataras/iris/issues/1473). +New Package-level Variables: + +- `iris.B, KB, MB, GB, TB, PB, EB` for byte units. +- `TLSNoRedirect` to disable automatic "http://" to "https://" redirections (see below) +- `CookieAllowReclaim`, `CookieAllowSubdomains`, `CookieSameSite`, `CookieSecure` and `CookieEncoding` to bring previously sessions-only features to all cookies in the request. + New Context Methods: +- `Context.AddCookieOptions(...CookieOption)` adds options for `SetCookie`, `SetCookieKV, UpsertCookie` and `RemoveCookie` methods for the current request. +- `Context.ClearCookieOptions()` clears any cookie options registered through `AddCookieOptions`. - `Context.SetVersion(constraint string)` force-sets an [API Version](https://github.com/kataras/iris/wiki/API-versioning) - `Context.SetLanguage(langCode string)` force-sets a language code from inside a middleare, similar to the `app.I18n.ExtractFunc` - `Context.ServeContentWithRate`, `ServeFileWithRate` and `SendFileWithRate` methods to throttle the "download" speed of the client @@ -421,6 +430,8 @@ New Context Methods: Breaking Changes: +- `iris.CookieEncode` and `CookieDecode` are replaced with the `iris.CookieEncoding`. +- `sessions#Config.Encode` and `Decode` are removed in favor of (the existing) `Encoding` field. - `versioning.GetVersion` now returns an empty string if version wasn't found. - Change the MIME type of `Javascript .js` and `JSONP` as the HTML specification now recommends to `"text/javascript"` instead of the obselete `"application/javascript"`. This change was pushed to the `Go` language itself as well. See . - Remove the last input argument of `enableGzipCompression` in `Context.ServeContent`, `ServeFile` methods. This was deprecated a few versions ago. A middleware (`app.Use(iris.Gzip)`) or a prior call to `Context.Gzip(true)` will enable gzip compression. Also these two methods and `Context.SendFile` one now support `Content-Range` and `Accept-Ranges` correctly out of the box (`net/http` had a bug, which is now fixed). diff --git a/_examples/authentication/oauth2/main.go b/_examples/authentication/oauth2/main.go index 4bf638e3..0e79e972 100644 --- a/_examples/authentication/oauth2/main.go +++ b/_examples/authentication/oauth2/main.go @@ -74,16 +74,14 @@ var sessionsManager *sessions.Sessions func init() { // attach a session manager cookieName := "mycustomsessionid" - // AES only supports key sizes of 16, 24 or 32 bytes. - // You either need to provide exactly that amount or you derive the key from what you type in. - hashKey := []byte("the-big-and-secret-fash-key-here") - blockKey := []byte("lot-secret-of-characters-big-too") + hashKey := securecookie.GenerateRandomKey(64) + blockKey := securecookie.GenerateRandomKey(32) secureCookie := securecookie.New(hashKey, blockKey) sessionsManager = sessions.New(sessions.Config{ - Cookie: cookieName, - Encode: secureCookie.Encode, - Decode: secureCookie.Decode, + Cookie: cookieName, + Encoding: secureCookie, + AllowReclaim: true, }) } diff --git a/_examples/cookies/basic/main_test.go b/_examples/cookies/basic/main_test.go index 403392bd..8dd99467 100644 --- a/_examples/cookies/basic/main_test.go +++ b/_examples/cookies/basic/main_test.go @@ -13,16 +13,16 @@ func TestCookiesBasic(t *testing.T) { cookieName, cookieValue := "my_cookie_name", "my_cookie_value" - // Test Set A Cookie. + // Test set a Cookie. t1 := e.GET(fmt.Sprintf("/cookies/%s/%s", cookieName, cookieValue)).Expect().Status(httptest.StatusOK) t1.Cookie(cookieName).Value().Equal(cookieValue) // validate cookie's existence, it should be there now. t1.Body().Contains(cookieValue) - // Test Retrieve A Cookie. + // Test retrieve a Cookie. t2 := e.GET(fmt.Sprintf("/cookies/%s", cookieName)).Expect().Status(httptest.StatusOK) t2.Body().Equal(cookieValue) - // Test Remove A Cookie. + // Test remove a Cookie. t3 := e.DELETE(fmt.Sprintf("/cookies/%s", cookieName)).Expect().Status(httptest.StatusOK) t3.Body().Contains(cookieName) diff --git a/_examples/cookies/securecookie/main.go b/_examples/cookies/securecookie/main.go index 40ee7052..bca6e0a5 100644 --- a/_examples/cookies/securecookie/main.go +++ b/_examples/cookies/securecookie/main.go @@ -11,49 +11,62 @@ import ( "github.com/gorilla/securecookie" ) -var ( - // AES only supports key sizes of 16, 24 or 32 bytes. - // You either need to provide exactly that amount or you derive the key from what you type in. - hashKey = []byte("the-big-and-secret-fash-key-here") - blockKey = []byte("lot-secret-of-characters-big-too") - sc = securecookie.New(hashKey, blockKey) -) +func main() { + app := newApp() + // http://localhost:8080/cookies/name/value + // http://localhost:8080/cookies/name + // http://localhost:8080/cookies/remove/name + app.Listen(":8080") +} func newApp() *iris.Application { app := iris.New() - // Set A Cookie. - app.Get("/cookies/{name}/{value}", func(ctx iris.Context) { - name := ctx.Params().Get("name") - value := ctx.Params().Get("value") + r := app.Party("/cookies") + { + r.Use(useSecureCookies()) - ctx.SetCookieKV(name, value, iris.CookieEncode(sc.Encode)) // <-- + // Set A Cookie. + r.Get("/{name}/{value}", func(ctx iris.Context) { + name := ctx.Params().Get("name") + value := ctx.Params().Get("value") - ctx.Writef("cookie added: %s = %s", name, value) - }) + ctx.SetCookieKV(name, value) - // Retrieve A Cookie. - app.Get("/cookies/{name}", func(ctx iris.Context) { - name := ctx.Params().Get("name") + ctx.Writef("cookie added: %s = %s", name, value) + }) - value := ctx.GetCookie(name, iris.CookieDecode(sc.Decode)) // <-- + // Retrieve A Cookie. + r.Get("/{name}", func(ctx iris.Context) { + name := ctx.Params().Get("name") - ctx.WriteString(value) - }) + value := ctx.GetCookie(name) - // Delete A Cookie. - app.Delete("/cookies/{name}", func(ctx iris.Context) { - name := ctx.Params().Get("name") + ctx.WriteString(value) + }) - ctx.RemoveCookie(name) // <-- + r.Get("/remove/{name}", func(ctx iris.Context) { + name := ctx.Params().Get("name") - ctx.Writef("cookie %s removed", name) - }) + ctx.RemoveCookie(name) + + ctx.Writef("cookie %s removed", name) + }) + } return app } -func main() { - app := newApp() - app.Listen(":8080") +func useSecureCookies() iris.Handler { + var ( + hashKey = securecookie.GenerateRandomKey(64) + blockKey = securecookie.GenerateRandomKey(32) + + s = securecookie.New(hashKey, blockKey) + ) + + return func(ctx iris.Context) { + ctx.AddCookieOptions(iris.CookieEncoding(s)) + ctx.Next() + } } diff --git a/_examples/cookies/securecookie/main_test.go b/_examples/cookies/securecookie/main_test.go index f6217fd9..0754c9bd 100644 --- a/_examples/cookies/securecookie/main_test.go +++ b/_examples/cookies/securecookie/main_test.go @@ -7,25 +7,25 @@ import ( "github.com/kataras/iris/v12/httptest" ) -func TestCookiesBasic(t *testing.T) { +func TestSecureCookie(t *testing.T) { app := newApp() e := httptest.New(t, app, httptest.URL("http://example.com")) cookieName, cookieValue := "my_cookie_name", "my_cookie_value" - // Test Set A Cookie. + // Test set a Cookie. t1 := e.GET(fmt.Sprintf("/cookies/%s/%s", cookieName, cookieValue)).Expect().Status(httptest.StatusOK) // note that this will not work because it doesn't always returns the same value: // cookieValueEncoded, _ := sc.Encode(cookieName, cookieValue) t1.Cookie(cookieName).Value().NotEqual(cookieValue) // validate cookie's existence and value is not on its raw form. t1.Body().Contains(cookieValue) - // Test Retrieve A Cookie. + // Test retrieve a Cookie. t2 := e.GET(fmt.Sprintf("/cookies/%s", cookieName)).Expect().Status(httptest.StatusOK) t2.Body().Equal(cookieValue) - // Test Remove A Cookie. - t3 := e.DELETE(fmt.Sprintf("/cookies/%s", cookieName)).Expect().Status(httptest.StatusOK) + // Test remove a Cookie. + t3 := e.GET(fmt.Sprintf("/cookies/remove/%s", cookieName)).Expect().Status(httptest.StatusOK) t3.Body().Contains(cookieName) t4 := e.GET(fmt.Sprintf("/cookies/%s", cookieName)).Expect().Status(httptest.StatusOK) diff --git a/_examples/http-listening/listen-addr-public/README.md b/_examples/http-listening/listen-addr-public/README.md deleted file mode 100644 index c29e185d..00000000 --- a/_examples/http-listening/listen-addr-public/README.md +++ /dev/null @@ -1 +0,0 @@ -![tunneling_screenshot.png](tunneling_screenshot.png) diff --git a/_examples/http-listening/listen-addr-public/main.go b/_examples/http-listening/listen-addr-public/main.go index f1423570..1e17cd0e 100644 --- a/_examples/http-listening/listen-addr-public/main.go +++ b/_examples/http-listening/listen-addr-public/main.go @@ -14,7 +14,7 @@ func main() { ctx.Application().ConfigurationReadOnly().GetVHost()) }) - app.Listen(":8080", iris.WithTunneling) + app.Listen(":8080", iris.WithTunneling, iris.WithLogLevel("debug")) /* The full configuration can be set as: app.Listen(":8080", iris.WithConfiguration( diff --git a/_examples/http-listening/listen-addr-public/tunneling_screenshot.png b/_examples/http-listening/listen-addr-public/tunneling_screenshot.png deleted file mode 100644 index df44adf963fda72514cb6f6697c5163f3f76c8b1..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 168290 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

(Xi!0!G?K&&t36 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

fwr^G4l&+k~`lSXSasFnn!yg=RT#{qX?si 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 G<^KWvjcW)1 diff --git a/_examples/http_request/read-json-struct-validation/main.go b/_examples/http_request/read-json-struct-validation/main.go index 59146255..29493183 100644 --- a/_examples/http_request/read-json-struct-validation/main.go +++ b/_examples/http_request/read-json-struct-validation/main.go @@ -10,7 +10,7 @@ import ( "github.com/kataras/iris/v12" - // $ go get github.com/go-playground/validator/v10 + // $ go get github.com/go-playground/validator/v10@latest "github.com/go-playground/validator/v10" ) diff --git a/_examples/sessions/securecookie/main.go b/_examples/sessions/securecookie/main.go index 00bfe01a..b2686626 100644 --- a/_examples/sessions/securecookie/main.go +++ b/_examples/sessions/securecookie/main.go @@ -20,14 +20,13 @@ func newApp() *iris.Application { cookieName := "_session_id" // AES only supports key sizes of 16, 24 or 32 bytes. // You either need to provide exactly that amount or you derive the key from what you type in. - hashKey := []byte("the-big-and-secret-fash-key-here") - blockKey := []byte("lot-secret-of-characters-big-too") - secureCookie := securecookie.New(hashKey, blockKey) + hashKey := securecookie.GenerateRandomKey(64) + blockKey := securecookie.GenerateRandomKey(32) + s := securecookie.New(hashKey, blockKey) mySessions := sessions.New(sessions.Config{ Cookie: cookieName, - Encode: secureCookie.Encode, - Decode: secureCookie.Decode, + Encoding: s, AllowReclaim: true, }) diff --git a/configuration.go b/configuration.go index 9eac65a3..cde41866 100644 --- a/configuration.go +++ b/configuration.go @@ -879,7 +879,7 @@ type Configuration struct { LanguageContextKey string `json:"languageContextKey,omitempty" yaml:"LanguageContextKey" toml:"LanguageContextKey"` // VersionContextKey is the context key which an API Version can be modified // via a middleware through `SetVersion` method, e.g. `ctx.SetVersion("1.0, 1.1")`. - // Defauls to "iris.api.version". + // Defaults to "iris.api.version". VersionContextKey string `json:"versionContextKey" yaml:"VersionContextKey" toml:"VersionContextKey"` // GetViewLayoutContextKey is the key of the context's user values' key // which is being used to set the template diff --git a/context/context.go b/context/context.go index ac6c3a6f..d5607132 100644 --- a/context/context.go +++ b/context/context.go @@ -36,6 +36,7 @@ import ( jsoniter "github.com/json-iterator/go" "github.com/microcosm-cc/bluemonday" "github.com/vmihailenco/msgpack/v5" + "golang.org/x/net/publicsuffix" "golang.org/x/time/rate" "gopkg.in/yaml.v3" ) @@ -984,6 +985,25 @@ type Context interface { // | Cookies | // +------------------------------------------------------------+ + // AddCookieOptions adds cookie options for `SetCookie`, + // `SetCookieKV, UpsertCookie` and `RemoveCookie` methods + // for the current request. It can be called from a middleware before + // cookies sent or received from the next Handler in the chain. + // See `ClearCookieOptions` too. + // + // Available builtin Cookie options are: + // * CookieSameSite + // * CookiePath + // * CookieCleanPath + // * CookieExpires + // * CookieHTTPOnly + // * CookieEncoding + // + // Example at: https://github.com/kataras/iris/tree/master/_examples/cookies/securecookie + AddCookieOptions(options ...CookieOption) + // ClearCookieOptions clears any previously registered cookie options. + // See `AddCookieOptions` too. + ClearCookieOptions() // SetCookie adds a cookie. // Use of the "options" is not required, they can be used to amend the "cookie". // @@ -994,14 +1014,6 @@ type Context interface { // if already set by a previous `SetCookie` call. // It reports whether the cookie is new (true) or an existing one was updated (false). UpsertCookie(cookie *http.Cookie, options ...CookieOption) bool - // SetSameSite sets a same-site rule for cookies to set. - // SameSite allows a server to define a cookie attribute making it impossible for - // the browser to send this cookie along with cross-site requests. The main - // goal is to mitigate the risk of cross-origin information leakage, and provide - // some protection against cross-site request forgery attacks. - // - // See https://tools.ietf.org/html/draft-ietf-httpbis-cookie-same-site-00 for details. - SetSameSite(sameSite http.SameSite) // SetCookieKV adds a cookie, requires the name(string) and the value(string). // // By default it expires at 2 hours and it's added to the root path, @@ -4734,48 +4746,171 @@ func (ctx *context) SendFileWithRate(src, destName string, limit float64, burst // | Cookies | // +------------------------------------------------------------+ +// Set of Cookie actions for `CookieOption`. +const ( + OpCookieGet uint8 = iota + OpCookieSet + OpCookieDel +) + // CookieOption is the type of function that is accepted on // context's methods like `SetCookieKV`, `RemoveCookie` and `SetCookie` // as their (last) variadic input argument to amend the end cookie's form. // // Any custom or builtin `CookieOption` is valid, // see `CookiePath`, `CookieCleanPath`, `CookieExpires` and `CookieHTTPOnly` for more. -type CookieOption func(*http.Cookie) +// The "op" is the operation code, 0 is GET, 1 is SET and 2 is REMOVE. +type CookieOption func(c *http.Cookie, op uint8) -// CookiePath is a `CookieOption`. -// Use it to change the cookie's Path field. -func CookiePath(path string) CookieOption { - return func(c *http.Cookie) { - c.Path = path +// findCookieAgainst reports whether the "cookie.Name" is in the list of "cookieNames". +// Notes: +// If "cookieNames" slice is empty then it returns true, +// If "cookie.Name" is empty then it returns false. +func findCookieAgainst(cookie *http.Cookie, cookieNames []string) bool { + if cookie.Name == "" { + return false + } + + if len(cookieNames) > 0 { + for _, name := range cookieNames { + if cookie.Name == name { + return true + } + } + + return false + } + + return true +} + +// CookieAllowReclaim accepts the Context itself. +// If set it will add the cookie to (on `CookieSet`, `CookieSetKV`, `CookieUpsert`) +// or remove the cookie from (on `CookieRemove`) the Request object too. +func CookieAllowReclaim(ctx Context, cookieNames ...string) CookieOption { + return func(c *http.Cookie, op uint8) { + if op == OpCookieGet { + return + } + + if !findCookieAgainst(c, cookieNames) { + return + } + + switch op { + case OpCookieSet: + ctx.Request().AddCookie(c) + case OpCookieDel: + // TODO: delete only this c.Name. + ctx.Request().Header.Set("Cookie", "") + } + } + +} + +// CookieAllowSubdomains set to the Cookie Options +// in order to allow subdomains to have access to the cookies. +// It sets the cookie's Domain field (if was empty) and +// it also sets the cookie's SameSite to lax mode too. +func CookieAllowSubdomains(ctx Context, cookieNames ...string) CookieOption { + host := ctx.Host() + if portIdx := strings.IndexByte(host, ':'); portIdx > 0 { + host = host[0:portIdx] + } + + cookieDomain := "." + host + + if domain, err := publicsuffix.EffectiveTLDPlusOne(host); err == nil { + cookieDomain = "." + domain + } + + return func(c *http.Cookie, _ uint8) { + if c.Domain != "" { + return // already set. + } + + if !findCookieAgainst(c, cookieNames) { + return + } + + c.Domain = cookieDomain + c.SameSite = http.SameSiteLaxMode // allow subdomain sharing. } } -// CookieCleanPath is a `CookieOption`. -// Use it to clear the cookie's Path field, exactly the same as `CookiePath("")`. -func CookieCleanPath(c *http.Cookie) { - c.Path = "" +// CookieSameSite sets a same-site rule for cookies to set. +// SameSite allows a server to define a cookie attribute making it impossible for +// the browser to send this cookie along with cross-site requests. The main +// goal is to mitigate the risk of cross-origin information leakage, and provide +// some protection against cross-site request forgery attacks. +// +// See https://tools.ietf.org/html/draft-ietf-httpbis-cookie-same-site-00 for details. +func CookieSameSite(sameSite http.SameSite) CookieOption { + return func(c *http.Cookie, op uint8) { + if op == OpCookieSet { + c.SameSite = sameSite + } + } } -// CookieExpires is a `CookieOption`. -// Use it to change the cookie's Expires and MaxAge fields by passing the lifetime of the cookie. -func CookieExpires(durFromNow time.Duration) CookieOption { - return func(c *http.Cookie) { - c.Expires = time.Now().Add(durFromNow) - c.MaxAge = int(durFromNow.Seconds()) +// CookieSecure sets the cookie's Secure option if the current request's +// connection is using TLS. See `CookieHTTPOnly` too. +func CookieSecure(ctx Context) CookieOption { + return func(c *http.Cookie, op uint8) { + if op == OpCookieSet { + if ctx.Request().TLS != nil { + c.Secure = true + } + } } } // CookieHTTPOnly is a `CookieOption`. // Use it to set the cookie's HttpOnly field to false or true. // HttpOnly field defaults to true for `RemoveCookie` and `SetCookieKV`. +// See `CookieSecure` too. func CookieHTTPOnly(httpOnly bool) CookieOption { - return func(c *http.Cookie) { - c.HttpOnly = httpOnly + return func(c *http.Cookie, op uint8) { + if op == OpCookieSet { + c.HttpOnly = httpOnly + } } } -type ( - // CookieEncoder should encode the cookie value. +// CookiePath is a `CookieOption`. +// Use it to change the cookie's Path field. +func CookiePath(path string) CookieOption { + return func(c *http.Cookie, op uint8) { + if op > OpCookieGet { // on set and remove. + c.Path = path + } + } +} + +// CookieCleanPath is a `CookieOption`. +// Use it to clear the cookie's Path field, exactly the same as `CookiePath("")`. +func CookieCleanPath(c *http.Cookie, op uint8) { + if op > OpCookieGet { + c.Path = "" + } +} + +// CookieExpires is a `CookieOption`. +// Use it to change the cookie's Expires and MaxAge fields by passing the lifetime of the cookie. +func CookieExpires(durFromNow time.Duration) CookieOption { + return func(c *http.Cookie, op uint8) { + if op == OpCookieSet { + c.Expires = time.Now().Add(durFromNow) + c.MaxAge = int(durFromNow.Seconds()) + } + } +} + +// SecureCookie should encodes and decodes +// authenticated and optionally encrypted cookie values. +// See `CookieEncoding` package-level function. +type SecureCookie interface { + // Encode should encode the cookie value. // Should accept the cookie's name as its first argument // and as second argument the cookie value ptr. // Should return an encoded value or an empty one if encode operation failed. @@ -4785,9 +4920,9 @@ type ( // and remember: if you use AES it only supports key sizes of 16, 24 or 32 bytes. // You either need to provide exactly that amount or you derive the key from what you type in. // - // See `CookieDecoder` too. - CookieEncoder func(cookieName string, value interface{}) (string, error) - // CookieDecoder should decode the cookie value. + // See `Decode` too. + Encode(cookieName string, cookieValue interface{}) (string, error) + // Decode should decode the cookie value. // Should accept the cookie's name as its first argument, // as second argument the encoded cookie value and as third argument the decoded value ptr. // Should return a decoded value or an empty one if decode operation failed. @@ -4797,39 +4932,100 @@ type ( // and remember: if you use AES it only supports key sizes of 16, 24 or 32 bytes. // You either need to provide exactly that amount or you derive the key from what you type in. // - // See `CookieEncoder` too. - CookieDecoder func(cookieName string, cookieValue string, v interface{}) error -) + // See `Encode` too. + Decode(cookieName string, cookieValue string, cookieValuePtr interface{}) error +} -// CookieEncode is a `CookieOption`. -// Provides encoding functionality when adding a cookie. -// Accepts a `CookieEncoder` and sets the cookie's value to the encoded value. -// Users of that is the `SetCookie` and `SetCookieKV`. +// CookieEncoding accepts a value which implements `Encode` and `Decode` methods. +// It calls its `Encode` on `Context.SetCookie, UpsertCookie, and SetCookieKV` methods. +// And on `Context.GetCookie` method it calls its `Decode`. +// If "cookieNames" slice is not empty then only cookies +// with that `Name` will be encoded on set and decoded on get, that way you can encrypt +// specific cookie names (like the session id) and let the rest of the cookies "insecure". // // Example: https://github.com/kataras/iris/tree/master/_examples/cookies/securecookie -func CookieEncode(encode CookieEncoder) CookieOption { - return func(c *http.Cookie) { - newVal, err := encode(c.Name, c.Value) - if err != nil { - c.Value = "" - } else { - c.Value = newVal +func CookieEncoding(encoding SecureCookie, cookieNames ...string) CookieOption { + return func(c *http.Cookie, op uint8) { + if op == OpCookieDel { + return + } + + if !findCookieAgainst(c, cookieNames) { + return + } + + switch op { + case OpCookieSet: + // Should encode, it's a write to the client operation. + newVal, err := encoding.Encode(c.Name, c.Value) + if err != nil { + c.Value = "" + } else { + c.Value = newVal + } + return + case OpCookieGet: + // Should decode, it's a read from the client operation. + if err := encoding.Decode(c.Name, c.Value, &c.Value); err != nil { + c.Value = "" + } } } } -// CookieDecode is a `CookieOption`. -// Provides decoding functionality when retrieving a cookie. -// Accepts a `CookieDecoder` and sets the cookie's value to the decoded value before return by the `GetCookie`. -// User of that is the `GetCookie`. +const cookieOptionsContextKey = "iris.cookie.options" + +// AddCookieOptions adds cookie options for `SetCookie`, +// `SetCookieKV, UpsertCookie` and `RemoveCookie` methods +// for the current request. It can be called from a middleware before +// cookies sent or received from the next Handler in the chain. // -// Example: https://github.com/kataras/iris/tree/master/_examples/cookies/securecookie -func CookieDecode(decode CookieDecoder) CookieOption { - return func(c *http.Cookie) { - if err := decode(c.Name, c.Value, &c.Value); err != nil { - c.Value = "" +// Available builtin Cookie options are: +// * CookieAllowReclaim +// * CookieAllowSubdomains +// * CookieSecure +// * CookieHTTPOnly +// * CookieSameSite +// * CookiePath +// * CookieCleanPath +// * CookieExpires +// * CookieEncoding +// +// Example at: https://github.com/kataras/iris/tree/master/_examples/cookies/securecookie +func (ctx *context) AddCookieOptions(options ...CookieOption) { + if len(options) == 0 { + return + } + + if v := ctx.Values().Get(cookieOptionsContextKey); v != nil { + if opts, ok := v.([]CookieOption); ok { + options = append(opts, options...) } } + + ctx.Values().Set(cookieOptionsContextKey, options) +} + +func (ctx *context) applyCookieOptions(c *http.Cookie, op uint8, override []CookieOption) { + if v := ctx.Values().Get(cookieOptionsContextKey); v != nil { + if options, ok := v.([]CookieOption); ok { + for _, opt := range options { + opt(c, op) + } + } + } + + // The function's ones should be called last, so they can override + // the stored ones (i.e by a prior middleware). + for _, opt := range override { + opt(c, op) + } +} + +// ClearCookieOptions clears any previously registered cookie options. +// See `AddCookieOptions` too. +func (ctx *context) ClearCookieOptions() { + ctx.Values().Remove(cookieOptionsContextKey) } // SetCookie adds a cookie. @@ -4837,29 +5033,22 @@ func CookieDecode(decode CookieDecoder) CookieOption { // // Example: https://github.com/kataras/iris/tree/master/_examples/cookies/basic func (ctx *context) SetCookie(cookie *http.Cookie, options ...CookieOption) { - cookie.SameSite = GetSameSite(ctx) - - for _, opt := range options { - opt(cookie) - } - + ctx.applyCookieOptions(cookie, OpCookieSet, options) http.SetCookie(ctx.writer, cookie) } +const setCookieHeaderKey = "Set-Cookie" + // UpsertCookie adds a cookie to the response like `SetCookie` does // but it will also perform a replacement of the cookie // if already set by a previous `SetCookie` call. // It reports whether the cookie is new (true) or an existing one was updated (false). func (ctx *context) UpsertCookie(cookie *http.Cookie, options ...CookieOption) bool { - cookie.SameSite = GetSameSite(ctx) - - for _, opt := range options { - opt(cookie) - } + ctx.applyCookieOptions(cookie, OpCookieSet, options) header := ctx.ResponseWriter().Header() - if cookies := header["Set-Cookie"]; len(cookies) > 0 { + if cookies := header[setCookieHeaderKey]; len(cookies) > 0 { s := cookie.Name + "=" // name=?value for i, c := range cookies { if strings.HasPrefix(c, s) { @@ -4867,40 +5056,21 @@ func (ctx *context) UpsertCookie(cookie *http.Cookie, options ...CookieOption) b // Probably the cookie is set and then updated in the first session creation // (e.g. UpdateExpiration, see https://github.com/kataras/iris/issues/1485). cookies[i] = cookie.String() - header["Set-Cookie"] = cookies + header[setCookieHeaderKey] = cookies return false } } } - header.Add("Set-Cookie", cookie.String()) + header.Add(setCookieHeaderKey, cookie.String()) return true } -const sameSiteContextKey = "iris.cookie_same_site" - -// SetSameSite sets a same-site rule for cookies to set. -// SameSite allows a server to define a cookie attribute making it impossible for -// the browser to send this cookie along with cross-site requests. The main -// goal is to mitigate the risk of cross-origin information leakage, and provide -// some protection against cross-site request forgery attacks. +// SetCookieKVExpiration is 365 days by-default +// you can change it or simple, use the SetCookie for more control. // -// See https://tools.ietf.org/html/draft-ietf-httpbis-cookie-same-site-00 for details. -func (ctx *context) SetSameSite(sameSite http.SameSite) { - ctx.Values().Set(sameSiteContextKey, sameSite) -} - -// GetSameSite returns the saved-to-context cookie http.SameSite option. -func GetSameSite(ctx Context) http.SameSite { - if v := ctx.Values().Get(sameSiteContextKey); v != nil { - sameSite, ok := v.(http.SameSite) - if ok { - return sameSite - } - } - - return http.SameSiteDefaultMode -} +// See CookieExpires` for more. +var SetCookieKVExpiration = time.Duration(8760) * time.Hour // SetCookieKV adds a cookie, requires the name(string) and the value(string). // @@ -4925,8 +5095,13 @@ func (ctx *context) SetCookieKV(name, value string, options ...CookieOption) { c.Name = name c.Value = url.QueryEscape(value) c.HttpOnly = true + + // MaxAge=0 means no 'Max-Age' attribute specified. + // MaxAge<0 means delete cookie now, equivalently 'Max-Age: 0' + // MaxAge>0 means Max-Age attribute present and given in seconds c.Expires = time.Now().Add(SetCookieKVExpiration) - c.MaxAge = int(SetCookieKVExpiration.Seconds()) + c.MaxAge = int(time.Until(c.Expires).Seconds()) + ctx.SetCookie(c, options...) } @@ -4938,24 +5113,24 @@ func (ctx *context) SetCookieKV(name, value string, options ...CookieOption) { // // Example: https://github.com/kataras/iris/tree/master/_examples/cookies/basic func (ctx *context) GetCookie(name string, options ...CookieOption) string { - cookie, err := ctx.request.Cookie(name) + c, err := ctx.request.Cookie(name) if err != nil { return "" } - for _, opt := range options { - opt(cookie) - } + ctx.applyCookieOptions(c, OpCookieGet, options) - value, _ := url.QueryUnescape(cookie.Value) + value, _ := url.QueryUnescape(c.Value) return value } -// SetCookieKVExpiration is 365 days by-default -// you can change it or simple, use the SetCookie for more control. -// -// See `SetCookieKVExpiration` and `CookieExpires` for more. -var SetCookieKVExpiration = time.Duration(8760) * time.Hour +var ( + // CookieExpireDelete may be set on Cookie.Expire for expiring the given cookie. + CookieExpireDelete = time.Date(2009, time.November, 10, 23, 0, 0, 0, time.UTC) + + // CookieExpireUnlimited indicates that does expires after 24 years. + CookieExpireUnlimited = time.Now().AddDate(24, 10, 10) +) // RemoveCookie deletes a cookie by its name and path = "/". // Tip: change the cookie's path to the current one by: RemoveCookie("name", iris.CookieCleanPath) @@ -4967,13 +5142,13 @@ func (ctx *context) RemoveCookie(name string, options ...CookieOption) { c.Value = "" c.Path = "/" // if user wants to change it, use of the CookieOption `CookiePath` is required if not `ctx.SetCookie`. c.HttpOnly = true + // RFC says 1 second, but let's do it 1 to make sure is working - exp := time.Now().Add(-time.Duration(1) * time.Minute) - c.Expires = exp + c.Expires = CookieExpireDelete c.MaxAge = -1 - ctx.SetCookie(c, options...) - // delete request's cookie also, which is temporary available. - ctx.request.Header.Set("Cookie", "") + + ctx.applyCookieOptions(c, OpCookieDel, options) + http.SetCookie(ctx.writer, c) } // VisitAllCookies takes a visitor function which is called diff --git a/iris.go b/iris.go index 199dea3e..ab70fecb 100644 --- a/iris.go +++ b/iris.go @@ -493,6 +493,41 @@ var ( // // A shortcut of the `cache#Cache304`. Cache304 = cache.Cache304 + + // CookieAllowReclaim accepts the Context itself. + // If set it will add the cookie to (on `CookieSet`, `CookieSetKV`, `CookieUpsert`) + // or remove the cookie from (on `CookieRemove`) the Request object too. + // + // A shortcut for the `context#CookieAllowReclaim`. + CookieAllowReclaim = context.CookieAllowReclaim + // CookieAllowSubdomains set to the Cookie Options + // in order to allow subdomains to have access to the cookies. + // It sets the cookie's Domain field (if was empty) and + // it also sets the cookie's SameSite to lax mode too. + // + // A shortcut for the `context#CookieAllowSubdomains`. + CookieAllowSubdomains = context.CookieAllowSubdomains + // CookieSameSite sets a same-site rule for cookies to set. + // SameSite allows a server to define a cookie attribute making it impossible for + // the browser to send this cookie along with cross-site requests. The main + // goal is to mitigate the risk of cross-origin information leakage, and provide + // some protection against cross-site request forgery attacks. + // + // See https://tools.ietf.org/html/draft-ietf-httpbis-cookie-same-site-00 for details. + // + // A shortcut for the `context#CookieSameSite`. + CookieSameSite = context.CookieHTTPOnly + // CookieSecure sets the cookie's Secure option if the current request's + // connection is using TLS. See `CookieHTTPOnly` too. + // + // A shortcut for the `context#CookieSecure`. + CookieSecure = context.CookieSecure + // CookieHTTPOnly is a `CookieOption`. + // Use it to set the cookie's HttpOnly field to false or true. + // HttpOnly field defaults to true for `RemoveCookie` and `SetCookieKV`. + // + // A shortcut for the `context#CookieHTTPOnly`. + CookieHTTPOnly = context.CookieHTTPOnly // CookiePath is a `CookieOption`. // Use it to change the cookie's Path field. // @@ -508,30 +543,13 @@ var ( // // A shortcut for the `context#CookieExpires`. CookieExpires = context.CookieExpires - // CookieHTTPOnly is a `CookieOption`. - // Use it to set the cookie's HttpOnly field to false or true. - // HttpOnly field defaults to true for `RemoveCookie` and `SetCookieKV`. + // CookieEncoding accepts a value which implements `Encode` and `Decode` methods. + // It calls its `Encode` on `Context.SetCookie, UpsertCookie, and SetCookieKV` methods. + // And on `Context.GetCookie` method it calls its `Decode`. // - // A shortcut for the `context#CookieHTTPOnly`. - CookieHTTPOnly = context.CookieHTTPOnly - // CookieEncode is a `CookieOption`. - // Provides encoding functionality when adding a cookie. - // Accepts a `context#CookieEncoder` and sets the cookie's value to the encoded value. - // Users of that is the `context#SetCookie` and `context#SetCookieKV`. - // - // Example: https://github.com/kataras/iris/tree/master/_examples/cookies/securecookie - // - // A shortcut for the `context#CookieEncode`. - CookieEncode = context.CookieEncode - // CookieDecode is a `CookieOption`. - // Provides decoding functionality when retrieving a cookie. - // Accepts a `context#CookieDecoder` and sets the cookie's value to the decoded value before return by the `GetCookie`. - // User of that is the `context#GetCookie`. - // - // Example: https://github.com/kataras/iris/tree/master/_examples/cookies/securecookie - // - // A shortcut for the `context#CookieDecode`. - CookieDecode = context.CookieDecode + // A shortcut for the `context#CookieEncoding`. + CookieEncoding = context.CookieEncoding + // IsErrPath can be used at `context#ReadForm`. // It reports whether the incoming error is type of `formbinder.ErrPath`, // which can be ignored when server allows unknown post values to be sent by the client. diff --git a/sessions/config.go b/sessions/config.go index 1e33d5b1..0951959a 100644 --- a/sessions/config.go +++ b/sessions/config.go @@ -13,33 +13,6 @@ const ( DefaultCookieName = "irissessionid" ) -// Encoding is the Cookie Encoder/Decoder interface, which can be passed as configuration field -// alternatively to the `Encode` and `Decode` fields. -type Encoding interface { - // Encode the cookie value if not nil. - // Should accept as first argument the cookie name (config.Name) - // as second argument the server's generated session id. - // Should return the new session id, if error the session id set to empty which is invalid. - // - // Note: Errors are not printed, so you have to know what you're doing, - // and remember: if you use AES it only supports key sizes of 16, 24 or 32 bytes. - // You either need to provide exactly that amount or you derive the key from what you type in. - // - // Defaults to nil - Encode(cookieName string, value interface{}) (string, error) - // Decode the cookie value if not nil. - // Should accept as first argument the cookie name (config.Name) - // as second second accepts the client's cookie value (the encoded session id). - // Should return an error if decode operation failed. - // - // Note: Errors are not printed, so you have to know what you're doing, - // and remember: if you use AES it only supports key sizes of 16, 24 or 32 bytes. - // You either need to provide exactly that amount or you derive the key from what you type in. - // - // Defaults to nil - Decode(cookieName string, cookieValue string, v interface{}) error -} - type ( // Config is the configuration for sessions. Please read it before using sessions. Config struct { @@ -66,34 +39,11 @@ type ( // Defaults to false. AllowReclaim bool - // Encode the cookie value if not nil. - // Should accept as first argument the cookie name (config.Cookie) - // as second argument the server's generated session id. - // Should return the new session id, if error the session id set to empty which is invalid. - // - // Note: Errors are not printed, so you have to know what you're doing, - // and remember: if you use AES it only supports key sizes of 16, 24 or 32 bytes. - // You either need to provide exactly that amount or you derive the key from what you type in. + // Encoding should encodes and decodes + // authenticated and optionally encrypted cookie values. // // Defaults to nil. - Encode func(cookieName string, value interface{}) (string, error) - // Decode the cookie value if not nil. - // Should accept as first argument the cookie name (config.Cookie) - // as second second accepts the client's cookie value (the encoded session id). - // Should return an error if decode operation failed. - // - // Note: Errors are not printed, so you have to know what you're doing, - // and remember: if you use AES it only supports key sizes of 16, 24 or 32 bytes. - // You either need to provide exactly that amount or you derive the key from what you type in. - // - // Defaults to nil. - Decode func(cookieName string, cookieValue string, v interface{}) error - - // Encoding same as Encode and Decode but receives a single instance which - // completes the "CookieEncoder" interface, `Encode` and `Decode` functions. - // - // Defaults to nil. - Encoding Encoding + Encoding context.SecureCookie // Expires the duration of which the cookie must expires (created_time.Add(Expires)). // If you want to delete the cookie when the browser closes, set it to -1. @@ -131,10 +81,5 @@ func (c Config) Validate() Config { } } - if c.Encoding != nil { - c.Encode = c.Encoding.Encode - c.Decode = c.Encoding.Decode - } - return c } diff --git a/sessions/cookie.go b/sessions/cookie.go deleted file mode 100644 index 8f21cd54..00000000 --- a/sessions/cookie.go +++ /dev/null @@ -1,142 +0,0 @@ -package sessions - -import ( - "net" - "net/http" - "strconv" - "strings" - "time" - - "github.com/kataras/iris/v12/context" - - "golang.org/x/net/publicsuffix" -) - -var ( - // CookieExpireDelete may be set on Cookie.Expire for expiring the given cookie. - CookieExpireDelete = time.Date(2009, time.November, 10, 23, 0, 0, 0, time.UTC) - - // CookieExpireUnlimited indicates that the cookie doesn't expire. - CookieExpireUnlimited = time.Now().AddDate(24, 10, 10) -) - -// GetCookie returns cookie's value by it's name -// returns empty string if nothing was found -func GetCookie(ctx context.Context, name string) string { - c, err := ctx.Request().Cookie(name) - if err != nil { - return "" - } - - return c.Value -} - -// AddCookie adds a cookie -func AddCookie(ctx context.Context, cookie *http.Cookie, reclaim bool) { - if reclaim { - ctx.Request().AddCookie(cookie) - } - - ctx.UpsertCookie(cookie) -} - -// RemoveCookie deletes a cookie by it's name/key -// If "purge" is true then it removes the, temp, cookie from the request as well. -func RemoveCookie(ctx context.Context, config Config) { - cookie, err := ctx.Request().Cookie(config.Cookie) - if err != nil { - return - } - - cookie.Expires = CookieExpireDelete - // MaxAge<0 means delete cookie now, equivalently 'Max-Age: 0' - cookie.MaxAge = -1 - cookie.Value = "" - cookie.Path = "/" - cookie.Domain = formatCookieDomain(ctx, config.DisableSubdomainPersistence) - - AddCookie(ctx, cookie, config.AllowReclaim) - - if config.AllowReclaim { - // delete request's cookie also, which is temporary available. - ctx.Request().Header.Set("Cookie", "") - } -} - -// IsValidCookieDomain returns true if the receiver is a valid domain to set -// valid means that is recognised as 'domain' by the browser, so it(the cookie) can be shared with subdomains also -func IsValidCookieDomain(domain string) bool { - if net.IP([]byte(domain)).IsLoopback() { - // for these type of hosts, we can't allow subdomains persistence, - // the web browser doesn't understand the mysubdomain.0.0.0.0 and mysubdomain.127.0.0.1 mysubdomain.32.196.56.181. as scorrectly ubdomains because of the many dots - // so don't set a cookie domain here, let browser handle this - return false - } - - dotLen := strings.Count(domain, ".") - if dotLen == 0 { - // we don't have a domain, maybe something like 'localhost', browser doesn't see the .localhost as wildcard subdomain+domain - return false - } - if dotLen >= 3 { - if lastDotIdx := strings.LastIndexByte(domain, '.'); lastDotIdx != -1 { - // chekc the last part, if it's number then propably it's ip - if len(domain) > lastDotIdx+1 { - _, err := strconv.Atoi(domain[lastDotIdx+1:]) - if err == nil { - return false - } - } - } - } - - return true -} - -// func formatCookieDomain(ctx context.Context, disableSubdomainPersistence bool) string { -// if disableSubdomainPersistence { -// return "" -// } - -// requestDomain := ctx.Host() -// if portIdx := strings.IndexByte(requestDomain, ':'); portIdx > 0 { -// requestDomain = requestDomain[0:portIdx] -// } - -// if !IsValidCookieDomain(requestDomain) { -// return "" -// } - -// // RFC2109, we allow level 1 subdomains, but no further -// // if we have localhost.com , we want the localhost.com. -// // so if we have something like: mysubdomain.localhost.com we want the localhost here -// // if we have mysubsubdomain.mysubdomain.localhost.com we want the .mysubdomain.localhost.com here -// // slow things here, especially the 'replace' but this is a good and understable( I hope) way to get the be able to set cookies from subdomains & domain with 1-level limit -// if dotIdx := strings.IndexByte(requestDomain, '.'); dotIdx > 0 { -// // is mysubdomain.localhost.com || mysubsubdomain.mysubdomain.localhost.com -// if strings.IndexByte(requestDomain[dotIdx+1:], '.') > 0 { -// requestDomain = requestDomain[dotIdx+1:] -// } -// } - -// // finally set the .localhost.com (for(1-level) || .mysubdomain.localhost.com (for 2-level subdomain allow) -// return "." + requestDomain // . to allow persistence -// } - -func formatCookieDomain(ctx context.Context, disableSubdomainPersistence bool) string { - if disableSubdomainPersistence { - return "" - } - - host := ctx.Host() - if portIdx := strings.IndexByte(host, ':'); portIdx > 0 { - host = host[0:portIdx] - } - - domain, err := publicsuffix.EffectiveTLDPlusOne(host) - if err != nil { - return "." + host - } - - return "." + domain -} diff --git a/sessions/lifetime.go b/sessions/lifetime.go index 3f79ce77..15efd675 100644 --- a/sessions/lifetime.go +++ b/sessions/lifetime.go @@ -2,6 +2,8 @@ package sessions import ( "time" + + "github.com/kataras/iris/v12/context" ) // LifeTime controls the session expiration datetime. @@ -50,7 +52,7 @@ func (lt *LifeTime) Shift(d time.Duration) { // ExpireNow reduce the lifetime completely. func (lt *LifeTime) ExpireNow() { - lt.Time = CookieExpireDelete + lt.Time = context.CookieExpireDelete if lt.timer != nil { lt.timer.Stop() } diff --git a/sessions/sessions.go b/sessions/sessions.go index 1b25c8c2..bcaf53d7 100644 --- a/sessions/sessions.go +++ b/sessions/sessions.go @@ -21,6 +21,8 @@ func init() { type Sessions struct { config Config provider *provider + + handlerCookieOpts []context.CookieOption // see `Handler`. } // New returns a new fast, feature-rich sessions manager @@ -38,52 +40,46 @@ func (s *Sessions) UseDatabase(db Database) { s.provider.RegisterDatabase(db) } +// GetCookieOptions returns any cookie options registered for the `Handler` method. +func (s *Sessions) GetCookieOptions() []context.CookieOption { + return s.handlerCookieOpts +} + // updateCookie gains the ability of updating the session browser cookie to any method which wants to update it func (s *Sessions) updateCookie(ctx context.Context, sid string, expires time.Duration, options ...context.CookieOption) { cookie := &http.Cookie{} // The RFC makes no mention of encoding url value, so here I think to encode both sessionid key and the value using the safe(to put and to use as cookie) url-encoding cookie.Name = s.config.Cookie - cookie.Value = sid cookie.Path = "/" - cookie.Domain = formatCookieDomain(ctx, s.config.DisableSubdomainPersistence) cookie.HttpOnly = true - if !s.config.DisableSubdomainPersistence { - cookie.SameSite = http.SameSiteLaxMode // allow subdomain sharing. - } // MaxAge=0 means no 'Max-Age' attribute specified. // MaxAge<0 means delete cookie now, equivalently 'Max-Age: 0' // MaxAge>0 means Max-Age attribute present and given in seconds if expires >= 0 { if expires == 0 { // unlimited life - cookie.Expires = CookieExpireUnlimited + cookie.Expires = context.CookieExpireUnlimited } else { // > 0 cookie.Expires = time.Now().Add(expires) } cookie.MaxAge = int(time.Until(cookie.Expires).Seconds()) } - // set the cookie to secure if this is a tls wrapped request - // and the configuration allows it. - if ctx.Request().TLS != nil && s.config.CookieSecureTLS { - cookie.Secure = true - } - - // encode the session id cookie client value right before send it. - cookie.Value = s.encodeCookieValue(cookie.Value) - - for _, opt := range options { - opt(cookie) - } - - AddCookie(ctx, cookie, s.config.AllowReclaim) + ctx.UpsertCookie(cookie, options...) } // Start creates or retrieves an existing session for the particular request. +// Note that `Start` method will not respect configuration's `AllowReclaim`, `DisableSubdomainPersistence`, `CookieSecureTLS`, +// and `Encoding` settings. +// Register sessions as a middleware through the `Handler` method instead, +// which provides automatic resolution of a *sessions.Session input argument +// on MVC and APIContainer as well. +// +// NOTE: Use `app.Use(sess.Handler())` instead, avoid using `Start` manually. func (s *Sessions) Start(ctx context.Context, cookieOptions ...context.CookieOption) *Session { - cookieValue := s.decodeCookieValue(GetCookie(ctx, s.config.Cookie)) + cookieValue := ctx.GetCookie(s.config.Cookie, cookieOptions...) if cookieValue == "" { // cookie doesn't exist, let's generate a session and set a cookie. sid := s.config.SessionIDGenerator(ctx) @@ -99,13 +95,34 @@ func (s *Sessions) Start(ctx context.Context, cookieOptions ...context.CookieOpt return s.provider.Read(s, cookieValue, s.config.Expires) } -const contextSessionKey = "iris.session" +const sessionContextKey = "iris.session" // Handler returns a sessions middleware to register on application routes. +// To return the request's Session call the `Get(ctx)` package-level function. +// +// Call `Handler()` once per sessions manager. func (s *Sessions) Handler(cookieOptions ...context.CookieOption) context.Handler { + s.handlerCookieOpts = cookieOptions + return func(ctx context.Context) { - session := s.Start(ctx, cookieOptions...) - ctx.Values().Set(contextSessionKey, session) + var requestOptions []context.CookieOption + if s.config.AllowReclaim { + requestOptions = append(requestOptions, context.CookieAllowReclaim(ctx, s.config.Cookie)) + } + if !s.config.DisableSubdomainPersistence { + requestOptions = append(requestOptions, context.CookieAllowSubdomains(ctx, s.config.Cookie)) + } + if s.config.CookieSecureTLS { + requestOptions = append(requestOptions, context.CookieSecure(ctx)) + } + if s.config.Encoding != nil { + requestOptions = append(requestOptions, context.CookieEncoding(s.config.Encoding, s.config.Cookie)) + } + ctx.AddCookieOptions(requestOptions...) // request life-cycle options. + + session := s.Start(ctx, cookieOptions...) // this cookie's end-developer's custom options. + + ctx.Values().Set(sessionContextKey, session) ctx.Next() } } @@ -116,14 +133,17 @@ func (s *Sessions) Handler(cookieOptions ...context.CookieOption) context.Handle // The `Sessions.Start` should be called previously, // e.g. register the `Sessions.Handler` as middleware. // Then call `Get` package-level function as many times as you want. -// The `Sessions.Start` can be called more than one time in the same request life cycle as well. +// Note: It will return nil if the session got destroyed by the same request. +// If you need to destroy and start a new session in the same request you need to call +// sessions manager's `Start` method after Destroy. func Get(ctx context.Context) *Session { - if v := ctx.Values().Get(contextSessionKey); v != nil { + if v := ctx.Values().Get(sessionContextKey); v != nil { if sess, ok := v.(*Session); ok { return sess } } + // ctx.Application().Logger().Debugf("Sessions: Get: no session found, prior Destroy(ctx) calls in the same request should follow with a Start(ctx) call too") return nil } @@ -144,7 +164,7 @@ func (s *Sessions) ShiftExpiration(ctx context.Context, cookieOptions ...context // It will return `ErrNotFound` when trying to update expiration on a non-existence or not valid session entry. // It will return `ErrNotImplemented` if a database is used and it does not support this feature, yet. func (s *Sessions) UpdateExpiration(ctx context.Context, expires time.Duration, cookieOptions ...context.CookieOption) error { - cookieValue := s.decodeCookieValue(GetCookie(ctx, s.config.Cookie)) + cookieValue := ctx.GetCookie(s.config.Cookie) if cookieValue == "" { return ErrNotFound } @@ -172,17 +192,20 @@ func (s *Sessions) OnDestroy(listeners ...DestroyListener) { } } -// Destroy remove the session data and remove the associated cookie. +// Destroy removes the session data, the associated cookie +// and the Context's session value. +// Next calls of `sessions.Get` will occur to a nil Session, +// use `Sessions#Start` method for renewal +// or use the Session's Destroy method which does keep the session entry with its values cleared. func (s *Sessions) Destroy(ctx context.Context) { - cookieValue := GetCookie(ctx, s.config.Cookie) - // decode the client's cookie value in order to find the server's session id - // to destroy the session data. - cookieValue = s.decodeCookieValue(cookieValue) + cookieValue := ctx.GetCookie(s.config.Cookie) if cookieValue == "" { // nothing to destroy return } - RemoveCookie(ctx, s.config) + ctx.Values().Remove(sessionContextKey) + + ctx.RemoveCookie(s.config.Cookie) s.provider.Destroy(cookieValue) } @@ -204,35 +227,3 @@ func (s *Sessions) DestroyByID(sid string) { func (s *Sessions) DestroyAll() { s.provider.DestroyAll() } - -// let's keep these funcs simple, we can do it with two lines but we may add more things in the future. -func (s *Sessions) decodeCookieValue(cookieValue string) string { - if cookieValue == "" { - return "" - } - - if decode := s.config.Decode; decode != nil { - var cookieValueDecoded string - err := decode(s.config.Cookie, cookieValue, &cookieValueDecoded) - if err == nil { - cookieValue = cookieValueDecoded - } else { - cookieValue = "" - } - } - - return cookieValue -} - -func (s *Sessions) encodeCookieValue(cookieValue string) string { - if encode := s.config.Encode; encode != nil { - newVal, err := encode(s.config.Cookie, cookieValue) - if err == nil { - cookieValue = newVal - } else { - cookieValue = "" - } - } - - return cookieValue -} diff --git a/sessions/sessions_test.go b/sessions/sessions_test.go index d459a7ab..7dfecaec 100644 --- a/sessions/sessions_test.go +++ b/sessions/sessions_test.go @@ -15,14 +15,16 @@ func TestSessions(t *testing.T) { app := iris.New() sess := sessions.New(sessions.Config{Cookie: "mycustomsessionid"}) - testSessions(t, sess, app) + app.Use(sess.Handler()) + + testSessions(t, app) } const ( testEnableSubdomain = true ) -func testSessions(t *testing.T, sess *sessions.Sessions, app *iris.Application) { +func testSessions(t *testing.T, app *iris.Application) { values := map[string]interface{}{ "Name": "iris", "Months": "4", @@ -30,7 +32,7 @@ func testSessions(t *testing.T, sess *sessions.Sessions, app *iris.Application) } writeValues := func(ctx context.Context) { - s := sess.Start(ctx) + s := sessions.Get(ctx) sessValues := s.GetAll() _, err := ctx.JSON(sessValues) @@ -44,7 +46,7 @@ func testSessions(t *testing.T, sess *sessions.Sessions, app *iris.Application) } app.Post("/set", func(ctx context.Context) { - s := sess.Start(ctx) + s := sessions.Get(ctx) vals := make(map[string]interface{}) if err := ctx.ReadJSON(&vals); err != nil { t.Fatalf("Cannot read JSON. Trace %s", err.Error()) @@ -59,26 +61,38 @@ func testSessions(t *testing.T, sess *sessions.Sessions, app *iris.Application) }) app.Get("/clear", func(ctx context.Context) { - sess.Start(ctx).Clear() + sessions.Get(ctx).Clear() writeValues(ctx) }) app.Get("/destroy", func(ctx context.Context) { - sess.Destroy(ctx) - writeValues(ctx) + session := sessions.Get(ctx) + if session.IsNew() { + t.Fatal("expected session not to be nil on destroy") + } + + session.Man.Destroy(ctx) + + if sessions.Get(ctx) != nil { + t.Fatal("expected session inside Context to be nil after Manager's Destroy call") + } + + ctx.JSON(struct{}{}) // the cookie and all values should be empty }) - // request cookie should be empty - app.Get("/after_destroy", func(ctx context.Context) { + // cookie should be new. + app.Get("/after_destroy_renew", func(ctx context.Context) { + isNew := sessions.Get(ctx).IsNew() + ctx.Writef("%v", isNew) }) app.Get("/multi_start_set_get", func(ctx context.Context) { - s := sess.Start(ctx) + s := sessions.Get(ctx) s.Set("key", "value") ctx.Next() }, func(ctx context.Context) { - s := sess.Start(ctx) + s := sessions.Get(ctx) _, err := ctx.Writef(s.GetString("key")) if err != nil { t.Fatal(err) @@ -98,12 +112,13 @@ func testSessions(t *testing.T, sess *sessions.Sessions, app *iris.Application) // test destroy which also clears first d := e.GET("/destroy").Expect().Status(iris.StatusOK) d.JSON().Object().Empty() - // This removed: d.Cookies().Empty(). Reason: - // httpexpect counts the cookies set or deleted at the response time, but cookie is not removed, to be really removed needs to SetExpire(now-1second) so, - // test if the cookies removed on the next request, like the browser's behavior. - e.GET("/after_destroy").Expect().Status(iris.StatusOK).Cookies().Empty() + + d = e.GET("/after_destroy_renew").Expect().Status(iris.StatusOK) + d.Body().Equal("true") + d.Cookies().NotEmpty() + // set and clear again - e.POST("/set").WithJSON(values).Expect().Status(iris.StatusOK).Cookies().NotEmpty() + e.POST("/set").WithJSON(values).Expect().Status(iris.StatusOK) e.GET("/clear").Expect().Status(iris.StatusOK).JSON().Object().Empty() // test start on the same request but more than one times