preview

package
v0.1.0 Latest Latest
Warning

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

Go to latest
Published: Aug 12, 2026 License: MIT Imports: 15 Imported by: 0

Documentation

Overview

Package preview issues and validates short-lived credentials for reaching a port inside a sandbox, and serves the reverse proxy that carries the traffic.

Tokens are self-describing and signed, so validating one is a local HMAC computation. Nothing is looked up, so the proxy needs no database and no control plane to call — which is the whole reason openblox can be a library rather than a service.

Index

Constants

View Source
const MaxTTL = 24 * time.Hour

MaxTTL bounds how long a preview credential may live. A preview is a way to look at something now, not a way to publish it.

View Source
const MinKeyBytes = 32

MinKeyBytes is the shortest accepted signing key. Below a full HMAC-SHA256 block of entropy the signature is the weakest link in the whole scheme.

View Source
const RoutePrefix = "/preview"

RoutePrefix is where a Handler expects to be mounted. Routes below it are "<prefix>/<sandbox>/<port>/<path…>".

Variables

View Source
var ErrInvalidToken = errors.New("invalid preview token")

ErrInvalidToken is returned for a token that is malformed, misapplied, expired, or not signed by this signer. It is deliberately one error: telling a caller which of those it was tells an attacker the same thing.

Functions

func ClampTTL

func ClampTTL(ttl, fallback time.Duration) time.Duration

ClampTTL bounds a requested lifetime to something a preview should have.

func ExpiresAt

func ExpiresAt(token string) (time.Time, bool)

ExpiresAt reports when token stops being valid. It does not authenticate the token; callers use it only after Verify, to expire cached bookkeeping.

func URL

func URL(base, sandboxName string, port int) string

URL returns the address a preview for port in a sandbox is served at, given the base address the Handler is reachable on.

Types

type Dialer

type Dialer interface {
	DialPort(ctx context.Context, name string, port int) (net.Conn, error)
}

Dialer opens a byte stream to a port inside a named sandbox.

type Handler

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

Handler proxies authenticated requests to ports inside sandboxes.

Mount it on a server the caller owns:

mux.Handle(preview.RoutePrefix+"/", preview.NewHandler(backend, signer))

openblox does not run the server. What the outside world may reach, on what address, behind what TLS, is a deployment decision, and a library that made it would be a service.

func NewHandler

func NewHandler(dialer Dialer, signer *Signer) *Handler

NewHandler returns a Handler serving previews for sandboxes reachable through dialer, authenticated with signer.

func (*Handler) Revoke

func (h *Handler) Revoke(token string)

Revoke withdraws a token before it expires.

This is best-effort by construction. Tokens are self-describing and validated locally, so nothing has to be consulted to accept one — the same property that removes the control plane means a revocation lives only in the process that recorded it. Expiry is the bound that always holds; keep preview lifetimes short and treat this as prompt cleanup, not containment.

func (*Handler) ServeHTTP

func (h *Handler) ServeHTTP(w http.ResponseWriter, r *http.Request)

type Signer

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

Signer mints and verifies preview tokens. It is safe for concurrent use, and several processes sharing a key produce and accept each other's tokens.

func NewSigner

func NewSigner(key []byte) (*Signer, error)

NewSigner returns a Signer over key, which must be at least MinKeyBytes long and should come from a CSPRNG. The same key must be configured everywhere tokens are minted or checked.

func (*Signer) Sign

func (s *Signer) Sign(sandboxName string, port int, expiresAt time.Time) (string, error)

Sign returns a bearer credential for a port in a sandbox, valid until expiresAt.

The result is a secret. Send it in an Authorization header and nowhere else: a credential in a query string is copied into access logs, browser history, bookmarks, and the Referer header of every outbound link the page makes.

func (*Signer) Verify

func (s *Signer) Verify(token, sandboxName string, port int, now time.Time) error

Verify reports whether token authorises this sandbox and port as of now.

The sandbox name and port come from the route being served, not from the token, so a token minted for one sandbox cannot be replayed against another.

Jump to

Keyboard shortcuts

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