middleware

package
v0.42.0 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Sep 17, 2026 License: MIT Imports: 6 Imported by: 0

Documentation

Overview

Package middleware provides two HTTP middlewares for cookies: EncryptCookies, which encrypts and decrypts cookie values, and AddQueuedCookiesToResponse, which flushes a cookie jar's queue onto the response.

Each is a struct with a Handle method. Handle takes the next handler and returns one, rather than taking the request and a closure, because the response here is written as the handler runs rather than held as a value that can still be changed; both middlewares wrap the http.ResponseWriter and do their work at the last moment before the header goes out.

EncryptCookies goes outside AddQueuedCookiesToResponse, so that a queued cookie is encrypted too:

r.Get("/", h, encrypt.Handle, queue.Handle)

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

func Except

func Except(cookies ...string)

Except marks the named cookies to never be encrypted, by any instance.

Duplicates are dropped.

It is global state, because the point is to declare the exception once at boot rather than on every instance that gets built. A test that touches it calls FlushState afterwards.

func FlushState

func FlushState()

FlushState empties the global never-encrypt list and clears the serialize flag. A test that called Except calls this to put the package back.

func Serialized

func Serialized(name string) bool

Serialized reports whether this cookie's contents are serialized before encryption.

It reads a global flag that is always false: no exported function sets it. The branch stays so the flag has a single reader if a future release needs to set it.

The name is taken and ignored: the flag is per application, not per cookie.

Types

type AddQueuedCookiesToResponse

type AddQueuedCookiesToResponse struct {
	// contains filtered or unexported fields
}

AddQueuedCookiesToResponse writes the cookies a handler queued on the jar onto the response, so that a handler never has to hold the http.ResponseWriter to set one.

It is a struct with a Handle method, and Handle has the shape pipeline.Middleware[http.Handler] wants, so the method value is the middleware:

queue := middleware.NewAddQueuedCookiesToResponse(jar)
r.Get("/", h, queue.Handle)

func NewAddQueuedCookiesToResponse

func NewAddQueuedCookiesToResponse(cookies *cookie.CookieJar) *AddQueuedCookiesToResponse

NewAddQueuedCookiesToResponse returns a middleware that flushes cookies queued on cookies onto the response.

func (*AddQueuedCookiesToResponse) Handle

Handle drains the jar's queue onto the response after next runs.

Go writes the response as the handler runs, so a middleware that waited for the handler to return would be adding headers that already went out. Handle therefore takes the next handler and returns one, which is what every middleware in this framework does, and it hangs the queue on the point of no return: the first WriteHeader or Write, or the handler returning without either.

It clones the jar for this request and puts the clone in the context, so the queue a handler fills is the queue this response drains. See cookie.WithCookieJar.

A queued cookie replaces one the handler already set under the same name, path and domain, rather than joining it: two Set-Cookie headers for the same cookie leave the browser to pick, and which one it picks is not something to build on.

type EncryptCookies

type EncryptCookies struct {
	// contains filtered or unexported fields
}

EncryptCookies decrypts the cookies on the way in and encrypts them on the way out, so a handler reads and writes plain values and the browser only ever holds ciphertext.

It is a struct with a Handle method, and Handle has the shape pipeline.Middleware[http.Handler] wants:

encrypt := middleware.NewEncryptCookies(encrypter)
encrypt.DisableFor("XSRF-TOKEN")
r.Get("/", h, encrypt.Handle)

It goes outside AddQueuedCookiesToResponse, so the cookies the jar queued are encrypted too.

func NewEncryptCookies

func NewEncryptCookies(encrypter *encryption.Encrypter) *EncryptCookies

NewEncryptCookies returns a middleware that encrypts and decrypts cookies with encrypter.

func (*EncryptCookies) DisableFor

func (m *EncryptCookies) DisableFor(name ...string)

DisableFor marks the named cookies to be read and written in the clear by this instance.

Names add up across calls, and a name listed twice is harmless.

The cookie that needs this is the CSRF token: JavaScript on the page has to read it to put it in a header, and it cannot decrypt.

func (*EncryptCookies) Handle

func (m *EncryptCookies) Handle(next http.Handler) http.Handler

Handle decrypts every cookie on the request, calls next, and encrypts every cookie on the response.

The decrypt step rewrites the request's Cookie header, so r.Cookie(name) gives a handler the plain value; nothing downstream sees ciphertext.

The encrypt half cannot wait for the handler to return, because by then the header is gone. It hangs off the first WriteHeader or Write, or off the handler returning without either, and rewrites every Set-Cookie in place.

func (*EncryptCookies) IsDisabled

func (m *EncryptCookies) IsDisabled(name string) bool

IsDisabled reports whether this cookie is left in the clear, by this instance's list or by the global one.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL