config

package
v1.0.0 Latest Latest
Warning

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

Go to latest
Published: Sep 3, 2026 License: Apache-2.0 Imports: 10 Imported by: 0

Documentation

Overview

Package config is the one configuration surface: a YAML file, the environment overrides, the overrides a composition passes to Load, and a check that nothing needed is missing or malformed. There is no defaulting layer and no reflection; a key that nothing reads does not belong here.

Index

Constants

View Source
const (
	DefaultFilesDir      = "data/files"
	DefaultFilesMaxBytes = 25 << 20
)

The defaults. Twenty-five megabytes is what a mail attachment limit taught everybody to expect; the directory is relative, so a laptop needs no absolute path and a container mounts a volume at it.

View Source
const DefaultReadTimeout = 30 * time.Second

DefaultReadTimeout is how long a client has to send a whole request when a deployment says nothing. Thirty seconds is generous for every route this application has except an upload on a bad connection, which is the one a deployment overrides it for.

View Source
const DefaultRetentionDays = 365

DefaultRetentionDays is a year, the shortest period the obligations that ask for an audit trail at all tend to accept.

Variables

This section is empty.

Functions

func Local

func Local(host string) bool

Local reports whether host is a name that only reaches this machine. The set is closed and short on purpose: anything cleverer is a rule somebody will find a way past. It is exported because the auth module asks the same question about the same key: a session cookie is marked Secure unless the application is being reached at a local name, and http://localhost is the one place a browser would refuse one.

Types

type Audit

type Audit struct {
	RetentionDays int `yaml:"retention_days"`
}

Audit is how long the audit trail is kept: the one thing modules/audit cannot decide for itself, because a retention period is a compliance obligation and a module that chose one would be choosing somebody else's. Zero means the default and not "forever" — a table nothing ever deletes from is an outage with a date on it, and "forever" is spelled with a large number.

type Auth

type Auth struct {
	OIDC OIDC `yaml:"oidc"`
}

Auth is what the auth module cannot decide for itself. Passwords and sessions need no configuration — the parameters are constants in the module, because a deployment that lowers them is a deployment that has weakened itself — so this is one optional identity provider and nothing else.

type Config

type Config struct {
	Server   Server   `yaml:"server"`
	Database Database `yaml:"database"`
	NATS     NATS     `yaml:"nats"`
	Log      Log      `yaml:"log"`
	Auth     Auth     `yaml:"auth"`
	Mail     Mail     `yaml:"mail"`
	Audit    Audit    `yaml:"audit"`
	Files    Files    `yaml:"files"`
}

Config is the whole configuration of the reference app. See config.example.yaml.

func Load

func Load(path string, overrides ...Override) (Config, error)

Load reads path, applies the composition's overrides, then the environment's, and validates the result.

The order is the whole point of the signature. The file is what a deployment wrote down; a composition's override is the value a client's overlay knows and the file cannot ("this client is served at collect.example.com"); the environment is last because it belongs to whoever is running the process, and an override that code could silently outrank is an override that does nothing — which is what PLATFORMKIT_SERVER_PUBLIC_HOST was in the flagship binary. Validation runs after all three, on the values that will be used.

type Database

type Database struct {
	URL        string `yaml:"url"`
	MigrateURL string `yaml:"migrate_url"`
}

Database holds the two roles: the app connects as one, migrations as the other.

type Files

type Files struct {
	Dir      string `yaml:"dir"`
	MaxBytes int64  `yaml:"max_bytes"`
	// QuotaBytes is the disk one tenant may hold, enforced at upload against
	// what that tenant already has. Zero means the module's default of a
	// gigabyte; a negative number means no quota, which is what a
	// single-tenant installation wants and a public sign-up must not have.
	QuotaBytes int64 `yaml:"quota_bytes"`
}

Files is where uploaded bytes go and how large one upload may be: the two things modules/file cannot decide for itself, because a directory is a deployment's disk and a limit is how much of it a deployment is willing to lose to one mistake.

type Log

type Log struct {
	Level string `yaml:"level"`
}

Log is the logging surface: one level.

type Mail

type Mail struct {
	Host     string `yaml:"host"`
	Port     int    `yaml:"port"`
	Username string `yaml:"username"`
	Password string `yaml:"password"`
	From     string `yaml:"from"`
}

Mail is the one outgoing mail server, and there is one sender behind it: SMTP is what every service worth naming speaks. An empty host means there is none, and then main wires the in-memory mailbox and says so at boot — a deployment without mail still records every notification and simply sends none.

Username and Password are optional, because a relay on a private network authenticates by being unreachable from anywhere else. From is not: a message with no sender is refused by the far end, hours later, in somebody else's log.

func (Mail) Enabled

func (m Mail) Enabled() bool

Enabled reports whether a mail server is configured.

type NATS

type NATS struct {
	URL string `yaml:"url"`
}

NATS is the JetStream endpoint the outbox relay publishes to.

type OIDC

type OIDC struct {
	Issuer       string `yaml:"issuer"`
	ClientID     string `yaml:"client_id"`
	ClientSecret string `yaml:"client_secret"`
	// RedirectPath is the path the provider sends the browser back to. The host
	// is the request's own, because every tenant is reached at its own host and
	// one registered redirect per host is what the provider expects.
	RedirectPath string `yaml:"redirect_path"`
}

OIDC is one OpenID Connect provider. An empty issuer means there is none, and then the two OIDC routes are not registered at all: a route that would answer "this application has no identity provider" is a route with nothing to say.

func (OIDC) Enabled

func (o OIDC) Enabled() bool

Enabled reports whether a provider is configured.

type Override

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

Override is one key a composition sets before the configuration is validated.

func Set

func Set(name, value string) Override

Set names a key — the same name the YAML file uses and the same name an error message names — and the value a composition gives it.

It exists because a client overlay that sets a host after Load has returned sets a value nothing checked: validation has already run, so a host with a scheme and a path in it becomes every link the application builds, and the key the overlay was going to fill in has already been refused as empty. An override belongs before validation or it is not an override, it is a correction nobody read. See Load.

type Server

type Server struct {
	Addr       string `yaml:"addr"`
	PublicHost string `yaml:"public_host"`
	// Docs serves /openapi.json, /openapi.yaml and /docs. They are public by
	// construction and they publish every route and every permission the
	// application has: a map worth having before an attack and worth
	// withholding during one. It defaults to false, so a deployment that says
	// nothing says no.
	Docs bool `yaml:"docs"`

	// ReadTimeout is how long a client has to send a whole request. It is a
	// key rather than a constant because the one number it has to accommodate
	// is a deployment's: an upload of files.max_bytes over a slow connection
	// takes as long as it takes, and thirty seconds is right for a laptop and
	// wrong for a deployment that accepts a gigabyte.
	//
	// There was no read timeout at all, and a review sent a body at a byte a
	// second and held the request — and, before the file module was made to
	// stream outside one, a database transaction — for as long as it liked.
	ReadTimeout time.Duration `yaml:"read_timeout"`
}

Server is where the app listens, what host it believes it is reached at, and whether it publishes its own documentation.

Jump to

Keyboard shortcuts

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