Skip to content

Configuration

vxnsin edited this page Sep 7, 2026 · 11 revisions

Configuration

Run warden setup once, and warden settings whenever you want to see or change what it wrote. Nothing below has to be done by hand.

$ warden setup
Ports to hand out [8000-8999]: 4000-4099
Ports never to hand out: 4200
Port warden itself listens on [7010]:
Reachable from other machines? [y/N]:
Does this warden report to another one? [y/N]:
Allow stopping processes over the API? [y/N]:

Enter accepts every default, so it is six keystrokes if you only came for the pool.

Where it writes

System Path
Windows %LOCALAPPDATA%\warden\warden.toml
Linux ~/.config/warden/warden.toml
macOS ~/Library/Application Support/warden/warden.toml

WARDEN_CONFIG points somewhere else, which is how two wardens on one machine keep out of each other's way.

Seeing what is in effect

$ warden settings
SETTING     VALUE       FROM
host        127.0.0.1   default
port        7010        config file
pool_start  4000        config file
pool_end    4099        config file
token       set         environment

The FROM column is the point of the command. "Why is the pool 4000-4099 when the file says otherwise" is the question that costs an afternoon, and this answers it. Secrets show as set rather than being printed.

warden settings set pool_end 4199
warden settings unset probe        # back to its default
warden settings --json            # for a script

A value is checked before it is written, so the file never holds something warden would refuse to start with. Setting one that the environment overrides says so, rather than looking like it worked.

Where a value can come from

The first of these with an answer wins:

  1. a flag on warden serve
  2. an environment variable — WARDEN_ and the setting's name in capitals
  3. a .env file in the directory the process starts in
  4. the config file
  5. the default

The environment is what a container or a systemd unit will use, and the file is for a machine somebody sits at. Both work together, and warden settings says which one you are actually getting.

# .env, beside the process
WARDEN_POOL_START=4000
WARDEN_TOKEN=a-long-random-string

Setting names below are the file's keys. As an environment variable each takes the WARDEN_ prefix in capitals: pool_start becomes WARDEN_POOL_START.

The registry itself

Setting Flag Default Meaning
host --host 127.0.0.1 Interface it listens on
port --port 7010 Port it listens on
database --database platform data directory SQLite file holding everything

The database defaults to %LOCALAPPDATA%\warden\registry.db on Windows, ~/.local/share/warden/registry.db on Linux and ~/Library/Application Support/warden/registry.db on macOS. It is created on first use, along with any missing parent directories.

The pool

Setting Flag Default Meaning
pool_start --pool 8000-8999 8000 First port that may be handed out
pool_end --pool 8000-8999 8999 Last port that may be handed out
reserved --reserved empty Ports never handed out
probe --no-probe true Test a port for an existing listener before handing it out

reserved takes single ports and ranges, separated by commas: 8080,8443,9000-9010.

The registry's own port is added to the reserved set automatically when it falls inside the pool. It lives on the same machine, so it could never be handed out anyway.

--no-probe turns off the bind test. Only worth it if something in your environment makes binding expensive; you lose the ability to notice ports that were taken outside the registry.

Access

Setting Default Meaning
token empty Guards everything, including anything that changes state
cluster_token empty The secret wardens use with each other: announcing, and reading
allow_kill false Let the API stop processes
allow_remote_update false Let a caller ask this warden to update itself
update_command empty What updating means on this machine
update_check true Ask GitHub whether a newer release exists
update_repo vxnsin/warden Which repository to ask about
update_interval 21600 Seconds between checks, at least 300

Empty means no check at all, which is fine while warden listens on loopback. Set token before binding to anything else — warden setup asks for one as soon as you say the machine should be reachable.

allow_kill is off on purpose. A warden reachable from the network would otherwise let anyone holding the token end processes on that machine, a far bigger thing to hand out than a port number. warden kill on the command line is unaffected; it acts locally and never asks the API.

Events going out

Setting Default Meaning
webhook empty Address events are posted to; must be http or https
webhook_format json json, discord, slack or teams
webhook_events all but renewed Which actions are worth posting
webhook_secret empty Key the posted body is signed with, for json

webhook_events takes a comma-separated list of registered, renewed, moved, released and expired. A name that is not one of those is refused by name rather than quietly ignored. renewed is left out by default: a channel told about every heartbeat is a channel people mute within the week.

The webhook applies to this warden only. In a fleet, every node reports its own events, so every node you want to hear from needs the setting.

See Events and webhooks.

The firewall

Setting Default Meaning
firewall_backend the machine's own nftables, iptables, pf or windows
firewall_rollback 60 Seconds to wait for a confirmation; 0 turns it off
firewall_from_registry false Let the registry's ports be opened at all
firewall_allow_from empty Networks a rule from the registry may open to

The last two are off and empty on purpose. Nothing declared is nothing allowed: a registry that could open ports out of the box would be a way around the firewall rather than a firewall. See Firewall.

The fleet

Setting Default Meaning
node the machine name This warden's name in the fleet
upstream empty Hub to report to; empty means this one is a hub
advertise from host and port Address the hub should use to reach it
node_ttl 90 Seconds a node's entry stays fresh (10 to 86400)
require_https false Refuse to register or send a token to a plain HTTP node

The machine name is lowercased and stripped of anything a service name would not accept, so BUILD-01.office.lan becomes build-01.office.lan rather than refusing to start.

A node reports three times per node_ttl, never more often than every five seconds.

See Cluster for what these do together.

For clients, not the server

Variable Flag Default Meaning
WARDEN_URL --url, -u http://127.0.0.1:7010 Which warden the CLI and the Python client talk to
WARDEN_TOKEN --token empty Token to send with each request

WARDEN_URL is what points warden ls at a warden on another machine. Note that warden ports and warden kill ignore it: they read the local machine directly.

Limits worth knowing

Thing Rule
Service name lowercase letters, digits, . _ -, starting with a letter or digit, up to 64 characters
Kind lowercase letters, digits and -, up to 32 characters
Project same shape as a service name
ttl on a registration 1 second to 24 hours
node_ttl 10 seconds to 24 hours
Ports 1 to 65535, and pool_start may not exceed pool_end

A setting outside its range stops warden at startup with a message naming the setting, rather than being quietly clamped. warden settings set refuses it before it ever reaches the file.

Clone this wiki locally