?::/h: Experimental

The ?::/h: query overrides response headers for a single request. Add ::/h:Header-Name=value to the query of any URL on a platform host to set a header, or ::/h:-=name to delete one.

Note: Header overrides are experimental and may change.

Syntax

plain
https://name.rt.ht/report.csv?::/h:content-disposition=attachment;filename=report.csv
https://name.rt.ht/nav.js?::/h:cross-origin-opener-policy=same-origin
https://name.rt.ht/nav.js?::/h:-=access-control-allow-origin,x-missing

Add one or more ::/h: parameters to the query of any URL on a platform host. The raw query string must contain the literal ::/h:. A percent-encoded form does not trigger it.

Parameters

::/h:<Header-Name>=<value>

Sets or replaces a header. Everything after the first = is the value.

::/h:-=<name>[,<name>…]

Deletes headers. The list is comma-separated, and the names are trimmed.

Combining parameters

Several parameters can be combined. For a repeated name, the last value wins. Deletes are applied before sets, so a header named in both is set.

Behavior

The override runs first, for every URL on a platform host: root pages, files, worker paths and other suffixes such as ::qr. RTEdge.net removes all ::/h: parameters and fetches the URL with the original method, headers and body. Status, body and the other headers pass through.

The rest of the query is re-serialized, so ?txt&::/h:x=1 reaches the router as ?txt= and loses the ?<ext> override: the response comes back as text/html;charset=utf-8. A query made only of ::/h: parameters reaches the router with no query.

Blocked headers

Some headers cannot be set or deleted. The match is a case-insensitive prefix match, so a blocked name also blocks every longer name that starts with it: te also blocks test, and server also blocks server-timing. The blocked names are the headers that the platform sets itself, and these:

plain
alt-svc, referrer-policy, content-length, transfer-encoding, content-security-policy, x-content-type-options, x-frame-options, x-xss-protection, strict-transport-security, x-dns-prefetch-control, clear-site-data, connection, proxy-authenticate, proxy-authorization, te, trailer, upgrade, server, date, via, location, www-authenticate, set-cookie, content-encoding, vary

A blocked name is skipped and listed in RT-Headers-Blocked.

Headers you can change

content-type, content-disposition, cache-control, etag, last-modified, the access-control-* headers, cross-origin-opener-policy, cross-origin-embedder-policy, cross-origin-resource-policy, permissions-policy, link, x-robots-tag and any custom header name.

Response

The response is the normal response of the URL, with your header changes and these report headers. Each is present only when it is not empty, and its value is comma-joined.

RT-Headers-Set-Old

Names that already existed and were overwritten.

RT-Headers-Set-New

Names that were added.

RT-Headers-Deleted

Names that were deleted and existed, in lower case.

RT-Headers-Blocked

Names that were rejected.

Access

Anyone can use it, on any URL. An override applies to that one request URL only, so a deployment cannot use it to set default headers. For headers that every response should carry, use the h:* attributes on exports.

Examples

Force a download

html
<a href="report.csv?::/h:content-disposition=attachment;filename=report.csv">Download the report</a>

The attribute is quoted because the value contains =. Everything after the first = is the header value. The response carries RT-Headers-Set-New: content-disposition.

Set a header on one request

plain
https://new.rt.ht/nav.js?::/h:cross-origin-opener-policy=same-origin&::/h:content-disposition=attachment

Both headers are set on the file for this URL only. The same query works on a suffix: https://new.rt.ht/::qr?::/h:content-disposition=attachment;filename=qr.svg returns the QR code with a download name.

Specifications

Not part of any specification. ?::/h: is an RTEdge.net feature. It changes these HTTP header fields:

Specification
HTTP Semantics (RFC 9110)
Use of the Content-Disposition Header Field in HTTP (RFC 6266)

Availability

FeaturePlaygroundRTEdge.netNotes
?::/h: ExperimentalNoYesNot emulated in the playground.

See also