refactor(routing): retire HOST_NAME — derive primary host from per-port subdomains

The static per-app CFG_<APP>_HOST_NAME is gone. host_setup (the app's
canonical FQDN, feeding the legacy single DOMAINSUBNAME_DATA used by app env
vars, the app URL and trusted-domains) is now derived from the app's primary
Traefik port's subdomain: first recommended port, else first Traefik port;
@/root -> apex, set -> sub.domain, empty -> app-name. Removes HOST_NAME from
all app configs, the config-form field mapping (Hostname), the dead
headscale stub, and wireguard.sh (now uses host_setup). Completes the move to
dynamic per-port subdomain routing.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Signed-off-by: librelad <librelad@digitalangels.vip>
This commit is contained in:
librelad 2026-05-22 11:25:00 +01:00
parent b17ac3707e
commit 2e4f4202e1
34 changed files with 24 additions and 79 deletions

View File

@ -43,12 +43,10 @@ CFG_ADGUARD_ACTIONS="configure|install|restart|shutdown|uninstall"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips on traefik, if false allow all
#
CFG_ADGUARD_DOMAIN=1
CFG_ADGUARD_WHITELIST=false
CFG_ADGUARD_HOST_NAME=adguard
CFG_ADGUARD_NETWORK=default
#
# =============================================================================

View File

@ -49,12 +49,10 @@ CFG_AUTHELIA_REQUIRES_SERVICE=traefik
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips (see general config), if false allow all
#
CFG_AUTHELIA_DOMAIN=1
CFG_AUTHELIA_WHITELIST=false
CFG_AUTHELIA_HOST_NAME=authelia
CFG_AUTHELIA_NETWORK=default
#
# =============================================================================

View File

@ -47,12 +47,10 @@ CFG_BOOKSTACK_ACTIONS="configure|install|restart|shutdown|uninstall"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips (see general config), if false allow all
#
CFG_BOOKSTACK_DOMAIN=1
CFG_BOOKSTACK_WHITELIST=false
CFG_BOOKSTACK_HOST_NAME=bookstack
CFG_BOOKSTACK_NETWORK=default
#
# =============================================================================

View File

@ -37,12 +37,10 @@ CFG_DASHY_ACTIONS="configure|install|restart|shutdown|uninstall|tools"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips (see general config), if false allow all
#
CFG_DASHY_DOMAIN=1
CFG_DASHY_WHITELIST=false
CFG_DASHY_HOST_NAME=dashy
CFG_DASHY_NETWORK=default
#
# =============================================================================

View File

@ -37,12 +37,10 @@ CFG_FOCALBOARD_ACTIONS="configure|install|restart|shutdown|uninstall"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips (see general config), if false allow all
#
CFG_FOCALBOARD_DOMAIN=1
CFG_FOCALBOARD_WHITELIST=false
CFG_FOCALBOARD_HOST_NAME=board
CFG_FOCALBOARD_NETWORK=default
# =============================================================================

View File

@ -41,12 +41,10 @@ CFG_GITEA_ACTIONS="configure|install|restart|shutdown|uninstall"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips (see general config), if false allow all
#
CFG_GITEA_DOMAIN=1
CFG_GITEA_WHITELIST=false
CFG_GITEA_HOST_NAME=gitea
CFG_GITEA_NETWORK=default
#
# =============================================================================

View File

@ -70,12 +70,10 @@ CFG_GLUETUN_ACTIONS="configure|install|restart|shutdown|uninstall"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips on traefik, if false allow all
#
CFG_GLUETUN_DOMAIN=1
CFG_GLUETUN_WHITELIST=false
CFG_GLUETUN_HOST_NAME=gluetun
CFG_GLUETUN_NETWORK=default
#
# =============================================================================

View File

@ -42,12 +42,10 @@ CFG_GRAFANA_REQUIRES_SERVICE=prometheus
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips (see general config), if false allow all
#
CFG_GRAFANA_DOMAIN=1
CFG_GRAFANA_WHITELIST=false
CFG_GRAFANA_HOST_NAME=grafana
CFG_GRAFANA_NETWORK=default
#
# =============================================================================

View File

@ -37,12 +37,10 @@ CFG_HEADSCALE_ACTIONS="configure|install|restart|shutdown|uninstall"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips (see general config), if false allow all
#
CFG_HEADSCALE_DOMAIN=1
CFG_HEADSCALE_WHITELIST=false
CFG_HEADSCALE_HOST_NAME=headscale
CFG_HEADSCALE_NETWORK=default
#
# =============================================================================

View File

@ -40,12 +40,10 @@ CFG_INVIDIOUS_ACTIONS="configure|install|restart|shutdown|uninstall|tools"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips (see general config), if false allow all
#
CFG_INVIDIOUS_DOMAIN=1
CFG_INVIDIOUS_WHITELIST=false
CFG_INVIDIOUS_HOST_NAME=invidious
CFG_INVIDIOUS_NETWORK=default
#
# =============================================================================

View File

@ -37,12 +37,10 @@ CFG_IPINFO_ACTIONS="configure|install|restart|shutdown|uninstall"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips (see general config), if false allow all
#
CFG_IPINFO_DOMAIN=1
CFG_IPINFO_WHITELIST=false
CFG_IPINFO_HOST_NAME=ipinfo
CFG_IPINFO_NETWORK=default
#
# =============================================================================

View File

@ -37,12 +37,10 @@ CFG_JELLYFIN_ACTIONS="configure|install|restart|shutdown|uninstall"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips (see general config), if false allow all
#
CFG_JELLYFIN_DOMAIN=1
CFG_JELLYFIN_WHITELIST=false
CFG_JELLYFIN_HOST_NAME=jellyfin
CFG_JELLYFIN_NETWORK=default
#
# =============================================================================

View File

@ -37,12 +37,10 @@ CFG_JITSIMEET_ACTIONS="configure|install|restart|shutdown|uninstall"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips (see general config), if false allow all
#
CFG_JITSIMEET_DOMAIN=1
CFG_JITSIMEET_WHITELIST=false
CFG_JITSIMEET_HOST_NAME=meet
CFG_JITSIMEET_NETWORK=default
#
# =============================================================================

View File

@ -39,12 +39,10 @@ CFG_LIBREPORTAL_ACTIONS="configure|install|restart|shutdown|tools"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips on traefik, if false allow all
#
CFG_LIBREPORTAL_DOMAIN=1
CFG_LIBREPORTAL_WHITELIST=false
CFG_LIBREPORTAL_HOST_NAME=libreportal
#
# =============================================================================
# PORT CONFIGURATION

View File

@ -37,12 +37,10 @@ CFG_LINKDING_ACTIONS="configure|install|restart|shutdown|uninstall"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips on traefik, if false allow all
#
CFG_LINKDING_DOMAIN=1
CFG_LINKDING_WHITELIST=false
CFG_LINKDING_HOST_NAME=bookmark
CFG_LINKDING_NETWORK=default
#
# =============================================================================

View File

@ -37,12 +37,10 @@ CFG_MASTODON_ACTIONS="configure|install|restart|shutdown|uninstall"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips on traefik, if false allow all
#
CFG_MASTODON_DOMAIN=1
CFG_MASTODON_WHITELIST=false
CFG_MASTODON_HOST_NAME=social
CFG_MASTODON_NETWORK=default
#
# =============================================================================

View File

@ -40,12 +40,10 @@ CFG_MONEYAPP_ACTIONS="configure|install|restart|shutdown|uninstall"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips (see general config), if false allow all
# NETWORK = default | gluetun (route outbound traffic through the VPN gateway)
#
CFG_MONEYAPP_DOMAIN=1
CFG_MONEYAPP_HOST_NAME=moneyapp
CFG_MONEYAPP_WHITELIST=false
CFG_MONEYAPP_NETWORK=default
#

View File

@ -49,12 +49,10 @@ CFG_NEXTCLOUD_ACTIONS="configure|install|restart|shutdown|uninstall|tools"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips on traefik, if false allow all
#
CFG_NEXTCLOUD_DOMAIN=1
CFG_NEXTCLOUD_WHITELIST=false
CFG_NEXTCLOUD_HOST_NAME=nextcloud
CFG_NEXTCLOUD_NETWORK=default
#
# =============================================================================

View File

@ -44,7 +44,6 @@ CFG_OLLAMA_ACTIONS="configure|install|restart|shutdown|uninstall"
#
CFG_OLLAMA_DOMAIN=1
CFG_OLLAMA_WHITELIST=false
CFG_OLLAMA_HOST_NAME=ollama
CFG_OLLAMA_NETWORK=default
#
# =============================================================================

View File

@ -42,7 +42,6 @@ CFG_ONLYOFFICE_ACTIONS="configure|install|restart|shutdown|uninstall"
#
CFG_ONLYOFFICE_DOMAIN=1
CFG_ONLYOFFICE_WHITELIST=false
CFG_ONLYOFFICE_HOST_NAME=onlyoffice
CFG_ONLYOFFICE_NETWORK=default
#
# =============================================================================

View File

@ -52,7 +52,6 @@ CFG_OWNCLOUD_ACTIONS="configure|install|restart|shutdown|uninstall"
#
CFG_OWNCLOUD_DOMAIN=1
CFG_OWNCLOUD_WHITELIST=false
CFG_OWNCLOUD_HOST_NAME=cloud
CFG_OWNCLOUD_NETWORK=default
#
# =============================================================================

View File

@ -48,12 +48,10 @@ CFG_PIHOLE_ACTIONS="configure|install|restart|shutdown|uninstall"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips on traefik, if false allow all
#
CFG_PIHOLE_DOMAIN=1
CFG_PIHOLE_WHITELIST=false
CFG_PIHOLE_HOST_NAME=pihole
CFG_PIHOLE_NETWORK=default
#
# =============================================================================

View File

@ -37,12 +37,10 @@ CFG_PROMETHEUS_ACTIONS="configure|install|restart|shutdown|uninstall"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips on traefik, if false allow all
#
CFG_PROMETHEUS_DOMAIN=1
CFG_PROMETHEUS_WHITELIST=false
CFG_PROMETHEUS_HOST_NAME=prometheus
CFG_PROMETHEUS_NETWORK=default
#
# =============================================================================

View File

@ -44,12 +44,10 @@ CFG_SEARXNG_ACTIONS="configure|install|restart|shutdown|uninstall"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips on traefik, if false allow all
#
CFG_SEARXNG_DOMAIN=1
CFG_SEARXNG_WHITELIST=false
CFG_SEARXNG_HOST_NAME=search
CFG_SEARXNG_NETWORK=default
#
# =============================================================================

View File

@ -45,12 +45,10 @@ CFG_SPEEDTEST_ACTIONS="configure|install|restart|shutdown|uninstall"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips on traefik, if false allow all
#
CFG_SPEEDTEST_DOMAIN=1
CFG_SPEEDTEST_WHITELIST=false
CFG_SPEEDTEST_HOST_NAME=speedtest
CFG_SPEEDTEST_NETWORK=default
#
# =============================================================================

View File

@ -58,12 +58,10 @@ CFG_TRAEFIK_ACTIONS="configure|install|restart|shutdown|uninstall"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips on traefik, if false allow all
#
CFG_TRAEFIK_DOMAIN=1
CFG_TRAEFIK_WHITELIST=false
CFG_TRAEFIK_HOST_NAME=traefik
CFG_TRAEFIK_NETWORK=default
#
# =============================================================================

View File

@ -37,12 +37,10 @@ CFG_TRILIUM_ACTIONS="configure|install|restart|shutdown|uninstall"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips on traefik, if false allow all
#
CFG_TRILIUM_DOMAIN=1
CFG_TRILIUM_WHITELIST=false
CFG_TRILIUM_HOST_NAME=notes
CFG_TRILIUM_NETWORK=default
#
# =============================================================================

View File

@ -39,12 +39,10 @@ CFG_UNBOUND_ACTIONS="configure|install|restart|shutdown|uninstall"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips on traefik, if false allow all
#
CFG_UNBOUND_DOMAIN=1
CFG_UNBOUND_WHITELIST=false
CFG_UNBOUND_HOST_NAME=unbound
CFG_UNBOUND_NETWORK=default
#
# =============================================================================

View File

@ -48,12 +48,10 @@ CFG_VAULTWARDEN_ACTIONS="configure|install|restart|shutdown|uninstall"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips on traefik, if false allow all
#
CFG_VAULTWARDEN_DOMAIN=1
CFG_VAULTWARDEN_WHITELIST=false
CFG_VAULTWARDEN_HOST_NAME=vault
CFG_VAULTWARDEN_NETWORK=default
#
# =============================================================================

View File

@ -51,12 +51,10 @@ CFG_WIREGUARD_ACTIONS="configure|install|restart|shutdown|uninstall"
# NETWORK CONFIGURATION
# =============================================================================
# DOMAIN = number of domain from the general config, useful when using multiple domains
# HOST_NAME = subdomain name e.g test is the name for test.website.com
# WHITELIST = if true only allow whitelisted ips on traefik, if false allow all
#
CFG_WIREGUARD_DOMAIN=1
CFG_WIREGUARD_WHITELIST=false
CFG_WIREGUARD_HOST_NAME=wireguard
CFG_WIREGUARD_NETWORK=default
#
# =============================================================================

View File

@ -96,7 +96,7 @@ installWireguard()
_wg_traefik_installed=1
fi
if [[ -n "$domain_full" && $_wg_traefik_installed -eq 1 ]]; then
wg_host_value="${CFG_WIREGUARD_HOST_NAME:-wireguard}.${domain_full}"
wg_host_value="$host_setup"
isNotice "Domain + Traefik present — peer configs will use $wg_host_value"
else
wg_host_value="${public_ip_v4:-127.0.0.1}"

View File

@ -12,14 +12,13 @@ setupHeadscaleVariables()
fi
# Build variable names based on app_name
headscale_host_name_var="CFG_${app_name^^}_HOST_NAME"
headscale_domain_var="CFG_${app_name^^}_DOMAIN"
headscale_setup_var="CFG_${app_name^^}_HEADSCALE"
# Access the variables using variable indirection
headscale_host_name="${!headscale_host_name_var}"
headscale_domain="${!headscale_domain_var}"
headscale_setup="${!headscale_setup_var}"
# (HOST_NAME read dropped in the per-port subdomain refactor — it was unused.)
# UNFINISHED
}

View File

@ -13,7 +13,6 @@ initializeAppVariables()
fi
# Build variable names based on app_name
host_name_var="CFG_${app_name^^}_HOST_NAME"
compose_setup_var="CFG_${app_name^^}_COMPOSE_FILE"
domain_var="CFG_${app_name^^}_DOMAIN"
whitelist_var="CFG_${app_name^^}_WHITELIST"
@ -24,7 +23,6 @@ initializeAppVariables()
app_title_var="CFG_${app_name^^}_TITLE"
# Access the variables using variable indirection
host_name="${!host_name_var}"
compose_setup="${!compose_setup_var}"
domain="${!domain_var}"
whitelist="${!whitelist_var}"
@ -35,18 +33,10 @@ initializeAppVariables()
app_title="${!app_title_var}"
domain_var_name="CFG_DOMAIN_${domain}"
domain_full="${!domain_var_name}"
# FQDN for this app's Traefik Host() rule (also feeds the app URL and
# trusted-domains):
# HOST_NAME="@" or "root" -> <domain> (apex / root of domain)
# HOST_NAME set -> <HOST_NAME>.<domain> (custom subdomain)
# HOST_NAME empty -> <app_name>.<domain> (fallback default)
if [[ "$host_name" == "@" || "$host_name" == "root" ]]; then
host_setup="${domain_full}"
else
host_setup="${host_name:-$app_name}.${domain_full}"
fi
ssl_key=${domain_full}.key
ssl_crt=${domain_full}.crt
# host_setup (the app's primary/canonical FQDN) is derived from the primary
# Traefik port's subdomain, computed after the port arrays are parsed below.
# Port configuration variables
port_config_vars=()
@ -164,4 +154,24 @@ initializeAppVariables()
for _t in "${port_traefik_managed[@]}"; do
[[ "$_t" == "true" ]] && { public="true"; break; }
done
# Primary/canonical host for this app: its first recommended Traefik port,
# else its first Traefik port. Feeds the legacy single DOMAINSUBNAME_DATA
# (app env vars), the app URL, and trusted-domains. Mirrors the per-port
# host rule (@/root -> apex, set -> sub.domain, empty -> app-name).
host_setup="${app_name}.${domain_full}"
local _i _primary=-1
for ((_i = 0; _i < ${#port_service_names[@]}; _i++)); do
[[ "${port_traefik_managed[$_i]}" == "true" ]] || continue
if [[ "${port_recommendeds[$_i]}" == "true" ]]; then _primary=$_i; break; fi
[[ $_primary -lt 0 ]] && _primary=$_i
done
if [[ $_primary -ge 0 ]]; then
local _sub="${port_subdomains[$_primary]}"
if [[ "$_sub" == "@" || "$_sub" == "root" ]]; then
host_setup="${domain_full}"
elif [[ -n "$_sub" ]]; then
host_setup="${_sub}.${domain_full}"
fi
fi
}

View File

@ -79,13 +79,6 @@ webuiCreateAppFieldMappings() {
"nonEditable": true,
"displayInfo": true
},
"HOST_NAME": {
"category": "network",
"label": "Hostname",
"type": "text",
"tooltip": "Subdomain this app is served on — e.g. myapp becomes myapp.yourdomain.com. Use @ to serve it on the root of your domain (yourdomain.com itself).",
"placeholder": "myapp · @ = root domain"
},
"DOMAIN": {
"category": "network",
"label": "Domain",