Documentation
¶
Overview ¶
Package blobserve writes stored binary content to an HTTP response.
Every raw-content endpoint in the platform — portal assets, asset versions, thumbnails, public share content, managed resources — serves bytes that a user uploaded or an upstream API produced, under a content type that came from the same untrusted place. They all need the same six things, and getting any of them wrong on one endpoint is a bug on that endpoint alone, which is why this is one function rather than a convention:
- A sandbox Content-Security-Policy, so bytes that reach a browser as a document cannot script the platform's origin whatever their type.
- X-Content-Type-Options: nosniff, so a browser cannot decide for itself that a text/plain response is really HTML and run it.
- A Content-Type reduced to a parsed, parameter-free media type, so a stored value like `text/plain; charset=utf-8"><script>` cannot smuggle anything into the header.
- Content-Disposition: attachment for the scriptable document families (HTML, XHTML, JSX, SVG, JavaScript, XML), which must never render inline on the platform's own origin, and inline for the passive families a viewer embeds.
- Byte-range support, so an audio or video element can seek without downloading the whole object first.
- A Cache-Control default of `private`, so an endpoint that authorizes its caller does not hand its bytes to a shared cache by saying nothing.
Index ¶
Constants ¶
const DefaultCacheControl = "private"
DefaultCacheControl is written when the caller set no Cache-Control of its own. Every endpoint reaching this package authorizes its caller first, and a response carrying no directive at all is heuristically storable by a shared cache: with ServeContent's Last-Modified as the freshness basis, a CDN or ingress cache in front of the platform may reuse one authorized fetch for every later request to the same URL, which is authorization bypass by omission. `private` says the browser that was authorized may keep it and no shared cache may.
Unlike the CSP above this is a default rather than an override: an endpoint whose bytes are genuinely anonymous — a fully public share's thumbnail — sets `public` deliberately, and that decision belongs to the handler that knows who may read the object.
It is exported because the surfaces that do not write through Serve — the gateway raw passthrough streams to its own sink — apply the same default, and the directive is the contract rather than each surface's opinion.
Variables ¶
This section is empty.
Functions ¶
func CachePrivate ¶ added in v1.117.0
func CachePrivate(w http.ResponseWriter, maxAge time.Duration)
CachePrivate marks the response as one only the caller that was authorized for it may keep: storable by that browser for maxAge, never by a shared cache, and keyed on the credential the browser sends so a cache that does store it cannot answer a second caller from the first one's copy.
It is one call rather than two Set lines per endpoint because the pairing is the point — a `private` that lost its Vary, or a Vary that lost its directive, is the same authorization bypass the pair exists to prevent. An endpoint whose bytes are genuinely anonymous writes `public` itself, so the exception stays visible at the one place that takes it.
func Headers ¶ added in v1.117.0
Headers returns the headers that decide how a browser treats untrusted bytes: the parsed, parameter-free Content-Type, the sandbox CSP, nosniff, and a Content-Disposition whose kind follows the type's family and whose filename cannot break out of its quoted parameter.
Only Name, ContentType and ForceAttachment are read; ModTime and Data describe a body this function does not write. It is separate from Serve for the surfaces that do not answer through an http.ResponseWriter — the gateway raw passthrough streams to its own sink — so the rendering decision is made once for every byte-serving surface rather than restated per transport. Cache-Control is not included: it is a default a caller may override, not a rendering decision, and DefaultCacheControl carries it.
Types ¶
type Options ¶
type Options struct {
// Name is the object's display filename. It is used for the
// Content-Disposition filename and must not be empty for downloads.
Name string
// ContentType is the stored media type. It is sanitized before it reaches
// the response; an empty or unparseable value serves as
// application/octet-stream.
ContentType string
// ModTime is the object's last-modified time, used for If-Range and
// conditional-request handling. The zero value disables both.
ModTime time.Time
// Data is the object's full content.
Data []byte
// ForceAttachment serves the blob as a download regardless of family. Set
// it on endpoints that exist to download, not to preview.
ForceAttachment bool
}
Options describes one blob to serve.