Skip to content

Configuration reference

The baseline settings were audited against b67fdde3. This reference also includes later stable releases and explicitly marked newer-master additions. The examples below show embedded defaults, not a recommended public deployment. Configure only the keys you need; never edit the embedded defaults.yaml in an installed server.

Location and precedence

The home directory is selected by RELAY_HOME, then legacy THELOUNGE_HOME, then ~/.relay. Without an explicit override, standalone Relay falls back to ~/.thelounge when only the legacy location contains config.yaml. The container normally uses /var/opt/relay; see installation for the legacy entrypoint caveat.

Configuration is merged in this order (last wins):

  1. Embedded defaults.
  2. <RELAY_HOME>/config.yaml.
  3. <RELAY_HOME>/admin-overrides.json, written by Administration.
  4. Repeated CLI -c key.path=value arguments.

Objects merge recursively; arrays replace the entire earlier array. Unknown top-level keys and type mismatches produce warnings. Use YAML booleans/numbers with the types shown below. A YAML edit can appear ineffective because an administrator override still wins. Inspect both files; stop Relay and back up the override file before manually removing conflicting entries. CLI overrides win at startup; live administrator changes may update the running value, and the CLI value returns on the next start.

relay start creates a starter YAML file and users/ if absent. Protect the data directory and secret-bearing YAML/JSON. Environment variables inside YAML are not a general interpolation mechanism: supply real values through a protected configuration-generation process.

Applying changes

File edits and CLI changes require a process restart. Administration writes supported settings to admin-overrides.json; it can persist all administrator-editable values, so later YAML edits may be masked even for controls you did not just change.

Change Application
Listener, TLS, proxy trust, IRC bind, public mode, file-only settings Restart server
Structured backend and PostgreSQL connection/pool Restart server to reopen providers
Registration and required local MFA Live server policy; weaker remembered sessions must authenticate again on reconnect
Client-visible media, theme and interface capabilities Use Apply Changes when offered to reload the browser; it is not a process restart
Upload enablement UI marks this as requiring restart; restart and verify upload route/capability
YAML retention policy or upload expiration Restart to initialize cleaners with the new policy

Restart Server exits with status 0 and requires a supervisor that restarts successful exits. See Server and users. Confirm a saved value after refreshing Administration and after a restart, especially if the service supplies -c flags.

Server and access

The default web listener binds all interfaces on port 9000; bind selects the local address for outbound IRC/ident, not the web listener. maxHistory is an in-memory channel message count (−1 means unlimited), separate from database retention. registrationMaxUsers: 0 means no self-registration cap. For trusted proxies and TLS paths, see HTTPS and reverse proxies.

public: false
host: null
port: 9000
bind: null
reverseProxy: false
trustedProxies:
- 127.0.0.0/8
- ::1/128
https:
  enable: false
  key: ''
  certificate: ''
  ca: ''
allowRegistration: false
registrationMaxUsers: 0
requireSecondFactor: false
networkGroups: true
maxHistory: 10000

Public resource limits

These budgets apply in public mode: counts for sessions/connections/channels, attempts per minute, events per second, byte limits for WebSocket messages and input, and a line count for input. Every value must be positive; per-IP limits cannot exceed global limits. Invalid or excessive budgets fail startup. Public mode also requires a valid default IRC host/port and rejects SASL EXTERNAL.

publicLimits:
  maxSessions: 128
  maxSessionsPerIp: 4
  maxIrcConnections: 64
  maxIrcConnectionsPerIp: 2
  ircAttemptsPerMinute: 6
  ircAttemptBurst: 2
  eventsPerSecond: 20
  eventBurst: 40
  maxWebSocketMessageBytes: 65536
  maxInputBytes: 8192
  maxInputLines: 16
  maxChannels: 32

IRC defaults and gateways

defaults seeds new connections; it does not rewrite saved private networks. Ports are TCP port numbers, join is a channel list, and % in the nickname becomes a random digit. Server password and SASL password are distinct. Public mode always locks transport settings; lockNetwork enables that boundary in private mode. webirc maps hosts to passwords or {password, hostnamePrefix} objects. oidentd is an output-file path; useHexIp enables IP-derived usernames. Coordinate gateway values with the IRC operator.

defaults:
  name: OUCHnet
  host: irc.ouch.chat
  port: 6697
  password: ''
  tls: true
  rejectUnauthorized: true
  nick: relay%%
  username: relay
  realname: ''
  join: '#relay'
  leaveMessage: ''
  sasl: ''
  saslAccount: ''
  saslPassword: ''
lockNetwork: false
leaveMessage: Relay - https://git.thc420.dev/ouch/relay
useHexIp: false
webirc: null
identd:
  enable: false
  port: 113
oidentd: null

History and retention

Relay 0.11.3 and later use storage for the shared database backend for history and short links. Legacy messageStorage and postgres settings remain readable, but use the current schema for new deployments and do not combine conflicting old and new values in one configuration layer. See storage configuration and migration.

Choose one primary backend (sqlite or postgres). messageHistory enables structured history and textLogs enables plain-text logging; the account logging flag must also allow writes. For PostgreSQL, set connection and pool options under storage.options as shown in Storage and retention. Retention age is days, with statusOnly or everything deletion policy.

storage:
  backend: sqlite
  options: {}
  messageHistory: true
  textLogs: true
storagePolicy:
  enabled: false
  maxAgeDays: 7
  deletionPolicy: statusOnly

Media, files and redirects

Image/search/upload/avatar/DCC size limits are KiB (the UI labels these KB); prefetchTimeout is milliseconds. Preview-cache byte limits are bytes, while DCC minFreeSpace is MiB. fileUpload.timeoutSeconds is seconds; its concurrency values bound simultaneous uploads globally and per user. Expiration is hours. Upload file size below one means unlimited. Upload/share expiration below one disables expiration; short links use zero for no expiry. DCC requires positive size, concurrency, expiration and free-space budgets before enabling. shortLink.minLength and codeLength are character counts. fileUpload.baseUrl and shortLink.baseUrl are optional URL strings (empty means the normal origin), omitted from the defaults below. Keep internal-address prefetch off unless you deliberately need it. See Media and files.

prefetch: false
disableMediaPreview: false
inlineVideoEmbeds: false
prefetchStorage: false
prefetchCache:
  maxBytes: 536870912
  maxFiles: 10000
  minFreeBytes: 268435456
prefetchMaxImageSize: 2048
prefetchMaxSearchSize: 50
prefetchTimeout: 5000
prefetchAllowInternalAddresses: false
fileUpload:
  timeoutSeconds: 900
  maxConcurrent: 16
  maxConcurrentPerUser: 2
  enable: false
  maxFileSize: 10240
  expirationTime: 24
avatars:
  enable: false
  maxFileSize: 2048
dcc:
  enable: false
  randomizeDownloadUrl: true
  listenAddress: 0.0.0.0:0
  advertiseAddress: ''
  maxFileSize: 0
  maxConcurrent: 0
  expirationTime: 0
  minFreeSpace: 0
shortLink:
  enable: false
  minLength: 100
  expirationTime: 720
  path: /s/
  codeLength: 6

Image metadata limit (newer master)

Master after 0.11.5 adds the following field (MiB, range 1–256):

fileUpload:
  maxImageScrubSize: 128

This is separate from maxFileSize (KiB). Restart after changing YAML, or use the live administrator control described in Media and files.

Authentication providers

In Relay 0.11.4, passwordRecoveryEnabled (default false) and passwordRecoveryUrl (default empty) control optional local password recovery. The URL must be the canonical HTTPS browser URL. Recovery additionally requires enabled SMTP with verified TLS and a bare sender email address; see setup and restrictions.

webauthn.rpId is a hostname, not a URL; an empty value derives it from the request. Use a stable HTTPS origin for keys. SMTP secure: true selects implicit TLS; false upgrades with STARTTLS when the SMTP server offers it. Scope is a space-separated string; username claim can be a nested claim path. See Authentication before enabling providers.

webauthn:
  rpId: ''
  rpName: Relay
smtp:
  enable: false
  host: localhost
  port: 587
  secure: false
  user: ''
  password: ''
  from: Relay <noreply@example.com>
oidc:
  enable: false
  issuer: ''
  clientId: ''
  clientSecret: ''
  scope: openid profile email
  usernameClaim: preferred_username

Appearance and integrations

themeColor is an optional browser theme-color string (empty by default). Logo URLs fall back to built-in branding when empty. Jitsi and KLIPY are disabled until configured. Debug raw IRC output can include sensitive content. See Integrations and branding.

theme: terminal
branding:
  logoEnabled: true
  logoUrl: ''
  logoInvertedUrl: ''
jitsi:
  enable: false
  serverUrl: https://ji.zrgw.dev
klipy:
  enable: false
  apiKey: ''
stats:
  commandEnable: true
  commandTemplate: '$nick IRC stats: Networks - $usernetworks || Channels - $userchannels
    || Total messages logged - $messageslogged || Storage - $storagebytes || Database
    - $databasebytes || Uptime - $uptime || Relay - $relayversion || OS - $os || Go
    - $go'
debug:
  ircFramework: false
  raw: false

The legacy desktop capability is removed in Relay 0.11.3; YAML cannot enable native desktop support. Socket.IO transports is not supported by the Go backend, which uses /ws.