{ config, lib, pkgs, ... }: let inherit (lib) mkIf; cfg = config.pepe.services.headscale; in { options.pepe.services.headscale = with lib; { enable = mkEnableOption "Enable Headscale"; package = mkPackageOption pkgs "headscale" { }; domain = mkOption { type = types.str; default = null; description = "Domain for the Headscale service."; }; port = mkOption { type = types.int; default = 1194; description = "Port for the Headscale service."; }; settings = mkOption { type = types.attrsOf types.str; default = { server_url = "https://${config.pepe.core.network.interfaces.tailscale.devices.architect.address}"; dns.magic_dns = false; dns.override_local_dns = true; dns.global = [ config.pepe.core.network.interfaces.tailscale.devices.architect.address ]; dns.nameservers.global = [ config.pepe.core.network.interfaces.tailscale.devices.architect.address ]; logtail.enabled = false; prefixes.v4 = config.pepe.core.network.interfaces.tailscale.net; noise.private_key_path = "/var/lib/headscale/noise_private.key"; }; description = "Configuration settings for Headscale."; }; }; config = mkIf cfg.enable { environment.systemPackages = [ cfg.package ]; services.headscale = { enable = true; package = cfg.package; port = cfg.port; settings = cfg.settings; }; pepe.core.vhost.hosts.${cfg.domain} = { dnsInterfaces = [ "lan" "tailscale" ]; locations."/" = { port = cfg.port; allowWAN = true; proxyWebsockets = true; }; }; pepe.core.firewall.openUDP = [ cfg.port ]; }; }