Documentation
¶
Overview ¶
Package referer provides middleware that captures the Referer request header, parses out its host, and stores the result on the request under the key "referer" for downstream handlers such as analytics and anti-CSRF checks. It ports the small but recurring Node pattern of reading req.headers.referer (or req.get('referrer')), normalizing it, and stashing it on the request/context so later handlers need not re-parse the header themselves.
Use it when several downstream consumers care about where a request came from: request logging and referral analytics, soft origin checks, or feeding a stricter allowlist gate (see the sibling referercheck package). Doing the parse once, up front, means handlers read a typed Referer value instead of repeatedly pulling and url.Parse-ing a raw header, and it centralizes the quirk that the header is misspelled "Referer" in the HTTP standard while some clients and codebases use the correct "Referrer".
Mechanically the middleware reads the "Referer" header, falling back to "Referrer" when the former is absent, wraps the raw value in a Referer struct, and — when the value is non-empty — parses it with net/url to fill in the Host field. It then stores the struct via req.Set(Key, ref) and always calls next(); it never writes a response, sets no response headers, and never short-circuits, so it is purely additive request state. Register it early via app.Use so the captured value is available to everything that follows, including any gate that decides whether to reject the request.
The captured value is always present but may be zero. A missing header yields a Referer with empty URL and empty Host; a present but unparseable header yields the raw URL with an empty Host, since a url.Parse error is swallowed rather than surfaced. Host is taken from the parsed URL's Host field, which includes the port when the referer carries one (for example "example.com:8443") — callers that want the bare hostname should strip the port themselves. Retrieve the value with From, which returns (Referer, false) when the middleware did not run or the stored value is of an unexpected type.
Parity with the Node original is behavioral: like the typical hand-rolled middleware it consults both header spellings, tolerates a missing or malformed value without erroring, and exposes a parsed host for convenience. It deliberately does not make any allow/deny decision — that policy belongs to a separate check so that capture and enforcement stay composable — and it does not attempt to reconstruct an origin (scheme + host) beyond what url.Parse reports.
Index ¶
Examples ¶
Constants ¶
const Key = "referer"
Key is the request value key under which the Referer info is stored.
Variables ¶
This section is empty.
Functions ¶
func New ¶
New returns middleware that stores a Referer via req.Set(Key, ref). Both the standard "Referer" and the (rare) correct spelling "Referrer" are consulted.
Example ¶
ExampleNew captures the Referer header once and reads it back downstream. The middleware is registered via app.Use so that the parsed value is available to every later handler through referer.From. A route then pulls the stored Referer and prints both its raw URL and its parsed Host, demonstrating that handlers consume a typed value instead of re-parsing the header. The request is driven through httptest with a Referer header set to a full URL including a path and query string. Because parsing is deterministic the example verifies the extracted URL and Host with an Output block.
package main
import (
"fmt"
"net/http"
"net/http/httptest"
"github.com/malcolmston/express"
"github.com/malcolmston/express/middleware/referer"
)
func main() {
app := express.New()
app.Use(referer.New())
app.Get("/", func(req *express.Request, res *express.Response, next express.Next) {
if ref, ok := referer.From(req); ok {
fmt.Printf("url: %s\n", ref.URL)
fmt.Printf("host: %s\n", ref.Host)
}
res.Send("ok")
})
rec := httptest.NewRecorder()
req := httptest.NewRequest(http.MethodGet, "/", nil)
req.Header.Set("Referer", "https://example.com/page?x=1")
app.ServeHTTP(rec, req)
}
Output: url: https://example.com/page?x=1 host: example.com