safeurl

package
v1.9.1 Latest Latest
Warning

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

Go to latest
Published: Nov 3, 2026 License: MIT Imports: 8 Imported by: 0

Documentation

Overview

Package safeurl decides whether an operator-supplied URL may be called from inside the service. A webhook URL is a request the service makes on someone else's say-so, so it must not reach anything the network keeps private: loopback, private ranges, link-local addresses (where cloud metadata lives), or the machine itself. The check runs on the resolved addresses and again at dial time, so a name cannot change its answer between the two.

Index

Constants

This section is empty.

Variables

View Source
var (
	// ErrScheme is returned for anything but https (or http under
	// AllowInsecure).
	ErrScheme = errors.New("safeurl: url must use https")
	// ErrHost is returned when the URL names no host.
	ErrHost = errors.New("safeurl: url has no host")
	// ErrUserinfo is returned when the URL carries credentials.
	ErrUserinfo = errors.New("safeurl: url must not carry credentials")
	// ErrNonPublic is returned when the host resolves to an address the
	// service must not call.
	ErrNonPublic = errors.New("safeurl: url points at a non-public address")
	// ErrResolve is returned when the host cannot be resolved at all.
	ErrResolve = errors.New("safeurl: host does not resolve")
)

Functions

func Client

func Client(timeout time.Duration, opts Options) *http.Client

Client returns an HTTP client for calling a validated URL. It resolves the host itself and dials only addresses that pass IsPublic, so a name whose answer changed since Validate is refused rather than followed; it never follows a redirect (the 3xx response is returned as is, for the caller to refuse); and it ignores proxy settings, which would otherwise carry the request somewhere the check never saw.

func IsPublic

func IsPublic(a netip.Addr) bool

IsPublic reports whether a is an address the service may call: not loopback, private, link-local (the cloud metadata address included), multicast, unspecified or reserved. IPv4-mapped IPv6 addresses are judged as the IPv4 address they carry.

func Validate

func Validate(ctx context.Context, raw string, opts Options) (*url.URL, error)

Validate parses raw and checks it may be called: https, a host, no credentials, and every address the host resolves to is public. It returns the parsed URL on success.

Types

type Options

type Options struct {
	// AllowInsecure permits http and non-public addresses. It is for
	// development against a receiver on the same machine and must never be
	// set in production.
	AllowInsecure bool
	// Resolver overrides name resolution; nil uses net.DefaultResolver.
	Resolver Resolver
}

Options tune a check.

type Resolver

type Resolver interface {
	LookupIPAddr(ctx context.Context, host string) ([]net.IPAddr, error)
}

Resolver looks a host name up. net.DefaultResolver satisfies it.

Jump to

Keyboard shortcuts

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