Description
This is a follow-up to #687, specifically: #687 (comment)
Background
To protect against cross-origin information leaks, exploitable by embedding a victim application's resources in an attacker-controlled document and inferring information about their contents, it would be useful to have a universal way to provide the application with information about the sender of the request with a request header. This would enable server-side decisions about whether to respond with sensitive resources depending on the context in which they are embedded, and could provide a robust way to protect against attacks such as CSRF, XS-Search, cross-origin timings and Spectre-like bugs.
This is conceptually similar to the Origin
header, but would need to be present on all resource requests (possibly only to origins which opt in) -- otherwise an attacker could embed the resource in a way which doesn't cause the header to be sent, without giving the server the opportunity to reject the request. Servers which want to add protection against cross-origin information leaks would inspect the value of the Sec-Site
header and could reject requests from origins they do not trust.
Details
From an adopter's point of view, the most useful variant would be identifying the source of the request with its origin, e.g.
Sec-Site: foo.example.org
In #687 (comment) @annevk mentioned some sensible concerns about sending the full origin value that I hope he can elaborate on here :) I expect that we can (and should!) make this feature fully compatible with the Referrer Policy by doing the following:
- If the request includes a
Referer
header that contains the origin, send the exact origin value. - If the request wouldn't otherwise have any identifying information about its origin, send one of
same-origin
,same-site
orcross-site
(spelling TBD).
This way most developers could write code such as:
if not request.headers.get("Sec-Site") in ["foo.example.org", "same-site"]: # reject
In applications which don't have a Referrer Policy of no-referrer
this would be even simpler because the developer could just rely on a URL whitelist.
I'd be a little wary of going with just the coarse-grained values because many applications have resources which are legitimately requested cross-origin, which wouldn't allow the developer to protect them. WDYT @annevk, would that be reasonable?
Questions
This is obviously just a sketch of the idea; if we want to pursue it more, we should probably think about the following issues:
- Should it be a per-origin opt-in (via Origin Policy) or enabled by default?
- Does it need a new header, or is there a benefit to overloading
Origin
instead (FWIW my guess is that would be ugly.) - Can we include some more metadata about the request, for example:
- Whether this request is a navigation, rather than a subresource load.
- The type of the resource that the request is going to be used as, e.g. "image" vs. "script"
- Naming: particularly if we add metadata, the header would no longer just identify the requesting site so we might need to rephrase it.
@mikewest certainly has some thoughts about this as well.