diff --git a/hosts/bastion/profiles/caddy/default.nix b/hosts/bastion/profiles/caddy/default.nix index 08196c8..46d8eea 100644 --- a/hosts/bastion/profiles/caddy/default.nix +++ b/hosts/bastion/profiles/caddy/default.nix @@ -284,7 +284,13 @@ "hass.e10.camp" = { host = hosts.controller; - port = 8123; + port = + hosts.controller.config.services.home-assistant.config.http.server_port; + }; + + "frigate.e10.camp" = { + host = hosts.htpc; + port = 8971; }; "e10.video" = { diff --git a/hosts/controller/configuration.nix b/hosts/controller/configuration.nix index a56d999..50b999a 100644 --- a/hosts/controller/configuration.nix +++ b/hosts/controller/configuration.nix @@ -2,6 +2,7 @@ imports = with suites; core ++ local ++ proxmox-vm ++ [ profiles.communications.mosquitto.default + profiles.hardware.bluetooth profiles.home-automation.home-assistant.default profiles.networking.blocky.default profiles.networking.speedtest-tracker diff --git a/hosts/monitor/profiles/authelia/default.nix b/hosts/monitor/profiles/authelia/default.nix index 07c76cb..7453f73 100644 --- a/hosts/monitor/profiles/authelia/default.nix +++ b/hosts/monitor/profiles/authelia/default.nix @@ -20,7 +20,7 @@ monitor_authelia_users_gatus_password_hash = secretConfig; }; - templates.monitor_authelia_users_file = { + templates."authelia/users.yml" = { content = lib.generators.toYAML { } { users = { admin = { @@ -73,7 +73,7 @@ settings = { authentication_backend.file = { - inherit (config.sops.templates.monitor_authelia_users_file) path; + inherit (config.sops.templates."authelia/users.yml") path; watch = false; password = { algorithm = "argon2"; diff --git a/hosts/monitor/profiles/prometheus.nix b/hosts/monitor/profiles/prometheus.nix index 7a58080..0ef608d 100644 --- a/hosts/monitor/profiles/prometheus.nix +++ b/hosts/monitor/profiles/prometheus.nix @@ -420,5 +420,11 @@ }]; scrape_interval = "30s"; } + { + job_name = "frigate"; + metrics_path = "/api/metrics"; + static_configs = [{ targets = [ "htpc:5000" ]; }]; + scrape_interval = "15s"; + } ]; } diff --git a/modules/nixos/services/tracearr/default.nix b/modules/nixos/services/tracearr/default.nix index 79e329c..077a84e 100644 --- a/modules/nixos/services/tracearr/default.nix +++ b/modules/nixos/services/tracearr/default.nix @@ -111,8 +111,12 @@ in { ensureDBOwnership = true; }]; } // mkIf cfg.database.enableTimescaleDB { - extensions = ps: with ps; [ timescaledb ]; + extensions = ps: with ps; [ timescaledb timescaledb_toolkit ]; settings = { shared_preload_libraries = [ "timescaledb" ]; }; + initialScriptText = lib.mkAfter '' + CREATE EXTENSION IF NOT EXISTS timescaledb; + CREATE EXTENSION IF NOT EXISTS timescaledb_toolkit; + ''; }; services.redis = mkIf cfg.redis.createLocally { diff --git a/modules/packages/tracearr/default.nix b/modules/packages/tracearr/default.nix index 99da7ec..2999c55 100644 --- a/modules/packages/tracearr/default.nix +++ b/modules/packages/tracearr/default.nix @@ -2,7 +2,7 @@ , fetchFromGitHub, turbo, }: stdenv.mkDerivation (finalAttrs: { pname = "tracearr"; - version = "1.4.12"; + version = "1.4.17"; src = fetchFromGitHub { owner = "connorgallopo"; diff --git a/modules/profiles/communications/mosquitto/secrets.json b/modules/profiles/communications/mosquitto/secrets.json index 98f6afe..5adb71e 100644 --- a/modules/profiles/communications/mosquitto/secrets.json +++ b/modules/profiles/communications/mosquitto/secrets.json @@ -36,8 +36,8 @@ "enc": "-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBKdjJsby9pTllzcGs0aWFk\nK0xEQndpSHY5VWR1eVRSeEw1ZlpJWHpzQTFRCnR1MzRwSUl5SkRkdWFqRWU2dnVq\nVmhnTU5wRzQ5ejVTQnpabzRpb1RuRE0KLS0tIHY5Y1gzNml0L1N5U2hPYjBIMmg1\ndjJpR3ROWUk2QkxvOWNCSm02NDh0UVkK+Adh/cckZJFQUKTmGtQUXl/6ONn/gPLt\nrpDbqSB3/kHVd/E+qh/Xf+p/bW53HjNJXtkk4LgGp9fwNx/M1koAqQ==\n-----END AGE ENCRYPTED FILE-----\n" } ], - "lastmodified": "2026-02-09T20:57:45Z", - "mac": "ENC[AES256_GCM,data:ETkHVqssQPw6T9hjg+lAXfzT8EtS1Q+X3jQit1BG6ZM6cZtlfKHo1XQhrtUAV2GBihogHpncDwTVn2pSrl5xZdaimepvAnMbSxfQMImrNyngmAUHsrFrfc83/dqGS9AnRGeMjlHT45PjN6dM4J+PRlLL3aOedScVWnPxpN9cL0Y=,iv:hV6d0+VpUF9RfAsgnwV3QVDDEQ/Z2a/eTcRFOPnbnB4=,tag:+gMp6YaQx8lEOd5rPXfiqw==,type:str]", + "lastmodified": "2026-02-12T21:50:27Z", + "mac": "ENC[AES256_GCM,data:uO8eMzLfLbCQ4rADQZJK/d7aIB6WQE036G8r3bq5jZ8NNL2CJy9HcfFwx93jByOcEbg+G5lajtCJCgBVVoWfhdGAZ71rh0tteBeeq71yezQWr2uB/E8Jyj2crq52R6TICDrepcYaukOql76z5uszLhzeSgRu9yXGK4g/Ipsmlfs=,iv:ITUZYy3AItVxByRVe8DIazx5ymGlCCG3u5I13XIFLbY=,tag:yIuXELaWgJSjrz1Lu3FbUA==,type:str]", "unencrypted_suffix": "_unencrypted", "version": "3.11.0" } diff --git a/modules/profiles/home-automation/frigate/default.nix b/modules/profiles/home-automation/frigate/default.nix index 9bc62ce..67ee919 100644 --- a/modules/profiles/home-automation/frigate/default.nix +++ b/modules/profiles/home-automation/frigate/default.nix @@ -1,5 +1,3 @@ -# TODO: MQTT for events from camera - { config, hosts, pkgs, ... }: let cameraAddress = "192.168.1.102"; @@ -75,15 +73,13 @@ in { frigate_tapo_sha256.sopsFile = ./secrets.json; }; - templates = { - "frigate/environment_file" = { - content = '' - FRIGATE_MQTT_PASSWORD=${config.sops.placeholder.frigate_mqtt_password} - FRIGATE_KITCHEN_PASSWORD=${config.sops.placeholder.frigate_kitchen_password} - FRIGATE_TAPO_SHA256=${config.sops.placeholder.frigate_tapo_sha256} - ''; - mode = "0777"; - }; + templates."frigate/environment_file" = { + content = '' + FRIGATE_MQTT_PASSWORD=${config.sops.placeholder.frigate_mqtt_password} + FRIGATE_KITCHEN_PASSWORD=${config.sops.placeholder.frigate_kitchen_password} + FRIGATE_TAPO_SHA256=${config.sops.placeholder.frigate_tapo_sha256} + ''; + mode = "0777"; }; }; diff --git a/modules/profiles/home-automation/home-assistant/default.nix b/modules/profiles/home-automation/home-assistant/default.nix index 48aff1b..0d31655 100644 --- a/modules/profiles/home-automation/home-assistant/default.nix +++ b/modules/profiles/home-automation/home-assistant/default.nix @@ -9,18 +9,16 @@ hass_oauth_secret.sopsFile = ./secrets.json; }; - templates = { - hass_secrets = { - content = '' - latitude: ${config.sops.placeholder.hass_latitude} - longitude: ${config.sops.placeholder.hass_longitude} - elevation: ${config.sops.placeholder.hass_elevation} + templates."hass/secrets.yaml" = { + content = '' + latitude: ${config.sops.placeholder.hass_latitude} + longitude: ${config.sops.placeholder.hass_longitude} + elevation: ${config.sops.placeholder.hass_elevation} - oauth_secret: ${config.sops.placeholder.hass_oauth_secret} - ''; - path = "/var/lib/hass/secrets.yaml"; - mode = "0777"; - }; + oauth_secret: ${config.sops.placeholder.hass_oauth_secret} + ''; + path = "/var/lib/hass/secrets.yaml"; + mode = "0777"; }; }; @@ -47,16 +45,20 @@ "brother" "ecobee" "google_translate" + "homeassistant_hardware" + "homeassistant_sky_connect" "homekit_controller" "hue" "ipp" "isal" + "matter" "met" "mqtt" "opower" "radio_browser" "sonos" "tplink" + "zha" ]; extraPackages = python3Packages: @@ -69,8 +71,8 @@ pyqrcode ]; - customComponents = [ - pkgs.home-assistant-custom-components.frigate + customComponents = with pkgs.home-assistant-custom-components; [ + frigate (pkgs.callPackage ./components/ha_nationalgrid.nix { aionatgrid = pkgs.python3Packages.callPackage ./packages/aionatgrid.nix { }; diff --git a/modules/profiles/media-management/bazarr/default.nix b/modules/profiles/media-management/bazarr/default.nix index f7f5a14..e6f3bcf 100644 --- a/modules/profiles/media-management/bazarr/default.nix +++ b/modules/profiles/media-management/bazarr/default.nix @@ -42,7 +42,7 @@ }; }; - templates."bazarr-config.yml" = { + templates."bazarr/config.yml" = { content = lib.generators.toYAML { } { addic7ed = { cookies = ""; diff --git a/modules/profiles/media-management/declutarr/default.nix b/modules/profiles/media-management/declutarr/default.nix index 2311b11..0dac329 100644 --- a/modules/profiles/media-management/declutarr/default.nix +++ b/modules/profiles/media-management/declutarr/default.nix @@ -1,5 +1,5 @@ { config, lib, ... }: { - sops.templates.declutarr_config = { + sops.templates."declutarr/config.yml" = { content = lib.generators.toYAML { } { general = { log_level = "INFO"; @@ -58,6 +58,6 @@ services.declutarr = { enable = true; - configFile = config.sops.templates.declutarr_config.path; + configFile = config.sops.templates."declutarr/config.yml".path; }; } diff --git a/modules/profiles/media-management/immich/default.nix b/modules/profiles/media-management/immich/default.nix index 5f518f2..637f217 100644 --- a/modules/profiles/media-management/immich/default.nix +++ b/modules/profiles/media-management/immich/default.nix @@ -7,7 +7,7 @@ }; }; - templates."immich-config.json" = { + templates."immich/config.json" = { content = builtins.toJSON { server = { externalDomain = "https://immich.e10.camp"; }; oauth = { @@ -42,7 +42,7 @@ mediaLocation = "/mnt/files/services/immich"; environment = { TZ = "America/New_York"; - IMMICH_CONFIG_FILE = config.sops.templates."immich-config.json".path; + IMMICH_CONFIG_FILE = config.sops.templates."immich/config.json".path; }; }; diff --git a/modules/profiles/media-management/radarr/default.nix b/modules/profiles/media-management/radarr/default.nix index 615accb..114d588 100644 --- a/modules/profiles/media-management/radarr/default.nix +++ b/modules/profiles/media-management/radarr/default.nix @@ -7,7 +7,7 @@ format = "yaml"; }; - templates."radarr-config.xml" = { + templates."radarr/config.xml" = { content = flake.lib.generators.toXML { rootName = "Config"; xmlns = { }; diff --git a/modules/profiles/media-management/sabnzbd/default.nix b/modules/profiles/media-management/sabnzbd/default.nix index 9b0d1e5..1eabdcf 100644 --- a/modules/profiles/media-management/sabnzbd/default.nix +++ b/modules/profiles/media-management/sabnzbd/default.nix @@ -77,7 +77,7 @@ }; }; - templates."sabnzbd-config.ini" = { + templates."sabnzbd/config.ini" = { content = flake.lib.generators.toINI { globalSection = { __version__ = 19; @@ -562,7 +562,7 @@ required = 0; optional = 0; retention = 0; - expire_date = "2026-01-30"; + expire_date = "2027-05-13"; quota = ""; usage_at_start = 0; priority = 0; @@ -644,7 +644,7 @@ services.sabnzbd = { enable = true; openFirewall = true; - configFile = config.sops.templates."sabnzbd-config.ini".path; + configFile = config.sops.templates."sabnzbd/config.ini".path; }; systemd.services.sabnzbd.serviceConfig.ExecStart = lib.mkOverride 10 "${ diff --git a/modules/profiles/media-management/sonarr/default.nix b/modules/profiles/media-management/sonarr/default.nix index f3c828a..e84a15e 100644 --- a/modules/profiles/media-management/sonarr/default.nix +++ b/modules/profiles/media-management/sonarr/default.nix @@ -7,7 +7,7 @@ format = "yaml"; }; - templates."sonarr-config.xml" = { + templates."sonarr/config.xml" = { content = flake.lib.generators.toXML { rootName = "Config"; xmlns = { }; diff --git a/modules/profiles/media-management/tracearr/default.nix b/modules/profiles/media-management/tracearr/default.nix index 7318b46..70bcfde 100644 --- a/modules/profiles/media-management/tracearr/default.nix +++ b/modules/profiles/media-management/tracearr/default.nix @@ -17,7 +17,7 @@ }; }; - templates.tracearr_environment_file = { + templates."tracearr/environment_file" = { content = '' MAXMIND_LICENSE_KEY=${config.sops.placeholder.maxmind_license_key} JWT_SECRET=${config.sops.placeholder.tracearr_jwt_secret} @@ -31,6 +31,6 @@ services.tracearr = { enable = true; openFirewall = true; - environmentFile = config.sops.templates.tracearr_environment_file.path; + environmentFile = config.sops.templates."tracearr/environment_file".path; }; } diff --git a/modules/profiles/monitoring/loki/default.nix b/modules/profiles/monitoring/loki/default.nix index 65eab3a..532b248 100644 --- a/modules/profiles/monitoring/loki/default.nix +++ b/modules/profiles/monitoring/loki/default.nix @@ -12,7 +12,7 @@ }; }; - templates.loki_environment_file = { + templates."loki/environment_file" = { content = '' AWS_ACCESS_KEY_ID=${config.sops.placeholder.loki_aws_access_key_id} AWS_SECRET_ACCESS_KEY=${config.sops.placeholder.loki_aws_secret_access_key} @@ -121,7 +121,7 @@ systemd.services.loki = { serviceConfig.EnvironmentFile = - config.sops.templates.loki_environment_file.path; + config.sops.templates."loki/environment_file".path; wants = [ "sops-nix.service" ]; after = [ "sops-nix.service" ]; }; diff --git a/modules/profiles/monitoring/thanos/default.nix b/modules/profiles/monitoring/thanos/default.nix index e679922..5910ba2 100644 --- a/modules/profiles/monitoring/thanos/default.nix +++ b/modules/profiles/monitoring/thanos/default.nix @@ -24,7 +24,7 @@ }; }; - templates.thanos_sidecar_object_storage_configuration = { + templates."thanos/sidecar_object_storage_configuration.json" = { content = builtins.toJSON { type = "S3"; config = { @@ -53,7 +53,7 @@ http.port = 19190; grpc.port = 10900; objstore.config-file = - config.sops.templates.thanos_sidecar_object_storage_configuration.path; + config.sops.templates."thanos/sidecar_object_storage_configuration.json".path; }; store = { @@ -61,7 +61,7 @@ http.port = 19191; grpc.port = 10901; objstore.config-file = - config.sops.templates.thanos_sidecar_object_storage_configuration.path; + config.sops.templates."thanos/sidecar_object_storage_configuration.json".path; }; query = { @@ -78,7 +78,7 @@ enable = true; http.port = 19193; objstore.config-file = - config.sops.templates.thanos_sidecar_object_storage_configuration.path; + config.sops.templates."thanos/sidecar_object_storage_configuration.json".path; }; }; diff --git a/modules/profiles/observability/gatus/default.nix b/modules/profiles/observability/gatus/default.nix index b56787c..4905539 100644 --- a/modules/profiles/observability/gatus/default.nix +++ b/modules/profiles/observability/gatus/default.nix @@ -10,7 +10,7 @@ in { config, lib, ... }: { gatus_ntfy_token.sopsFile = ./secrets.json; }; - templates.gatus_environment_file = { + templates."gatus/environment_file" = { content = '' GATUS_LOG_LEVEL=warn @@ -25,7 +25,7 @@ in { config, lib, ... }: { services.gatus = { enable = true; openFirewall = true; - environmentFile = config.sops.templates.gatus_environment_file.path; + environmentFile = config.sops.templates."gatus/environment_file".path; settings = { metrics = true; storage = { @@ -221,7 +221,7 @@ in { config, lib, ... }: { }) (mkEndpoint { name = "Frigate"; - url = "http://htpc:5000"; + url = "https://frigate.e10.camp"; group = "HTPC"; }) ]; diff --git a/modules/profiles/services/glance/default.nix b/modules/profiles/services/glance/default.nix index 4af86e5..58bb0b6 100644 --- a/modules/profiles/services/glance/default.nix +++ b/modules/profiles/services/glance/default.nix @@ -5,7 +5,7 @@ glance_authelia_basic_auth_password = { sopsFile = ./secrets.json; }; }; - templates.glance_environment_file = { + templates."glance/environment_file" = { content = '' AUTHELIA_BASIC_AUTH_USERNAME=${config.sops.placeholder.glance_authelia_basic_auth_username} AUTHELIA_BASIC_AUTH_PASSWORD=${config.sops.placeholder.glance_authelia_basic_auth_password} @@ -16,7 +16,7 @@ services.glance = { enable = true; - environmentFile = config.sops.templates.glance_environment_file.path; + environmentFile = config.sops.templates."glance/environment_file".path; settings = { server = { host = "0.0.0.0"; @@ -87,7 +87,7 @@ }) (mkSite { title = "Frigate"; - url = "http://htpc:5000"; + url = "https://frigate.e10.camp"; icon = "di:frigate"; }) (mkSite { diff --git a/modules/profiles/services/karakeep/default.nix b/modules/profiles/services/karakeep/default.nix index d02797b..46206cb 100644 --- a/modules/profiles/services/karakeep/default.nix +++ b/modules/profiles/services/karakeep/default.nix @@ -5,7 +5,7 @@ karakeep_oauth_secret.sopsFile = ./secrets.json; }; - templates.karakeep_environment_file = { + templates."karakeep/environment_file" = { content = '' NEXTAUTH_SECRET=${config.sops.placeholder.karakeep_nextauth_secret} OAUTH_CLIENT_SECRET=${config.sops.placeholder.karakeep_oauth_secret} @@ -44,6 +44,6 @@ OAUTH_PROVIDER_NAME = "Authelia"; OAUTH_ALLOW_DANGEROUS_EMAIL_ACCOUNT_LINKING = "true"; }; - environmentFile = config.sops.templates.karakeep_environment_file.path; + environmentFile = config.sops.templates."karakeep/environment_file".path; }; } diff --git a/modules/profiles/services/paperless/default.nix b/modules/profiles/services/paperless/default.nix index ec669fc..a05faa2 100644 --- a/modules/profiles/services/paperless/default.nix +++ b/modules/profiles/services/paperless/default.nix @@ -16,7 +16,7 @@ }; }; - templates.paperless_environment_file.content = '' + templates."paperless/environment_file".content = '' PAPERLESS_SOCIALACCOUNT_PROVIDERS='${config.sops.placeholder.paperless_socialaccount_providers}' ''; }; @@ -31,7 +31,7 @@ address = "0.0.0.0"; passwordFile = config.sops.secrets.paperless_admin_password.path; dataDir = "/mnt/files/services/paperless"; - environmentFile = config.sops.templates.paperless_environment_file.path; + environmentFile = config.sops.templates."paperless/environment_file".path; settings = { PAPERLESS_URL = "https://paperless.e10.camp"; USE_X_FORWARD_HOST = true; diff --git a/modules/profiles/services/termix/default.nix b/modules/profiles/services/termix/default.nix index d79ff48..0a10d1b 100644 --- a/modules/profiles/services/termix/default.nix +++ b/modules/profiles/services/termix/default.nix @@ -7,7 +7,7 @@ }; }; - templates.termix_environment_file = { + templates."termix/environment_file" = { content = '' OIDC_ENABLED=true OIDC_CLIENT_ID=BhZjM_kfrPU38DOigEa9HToE2XTdYsmSMOxUBmUOgxLkZr4xMB45u2E8QoJYlqe3hwJMReZy @@ -23,7 +23,7 @@ services.termix = { enable = true; - environmentFile = config.sops.templates.termix_environment_file.path; + environmentFile = config.sops.templates."termix/environment_file".path; openFirewall = true; }; } diff --git a/modules/profiles/telemetry/prometheus-plex-media-server-exporter/default.nix b/modules/profiles/telemetry/prometheus-plex-media-server-exporter/default.nix index b9bd799..b776bc3 100644 --- a/modules/profiles/telemetry/prometheus-plex-media-server-exporter/default.nix +++ b/modules/profiles/telemetry/prometheus-plex-media-server-exporter/default.nix @@ -5,7 +5,7 @@ format = "yaml"; }; - templates."prometheus-plex-media-server-exporter-secrets-file" = { + templates."prometheus-plex-media-server-exporter/secrets" = { content = '' PLEX_TOKEN=${config.sops.placeholder.plex_token} ''; @@ -16,7 +16,7 @@ enable = true; url = "https://e10.video"; secretsFile = - config.sops.templates."prometheus-plex-media-server-exporter-secrets-file".path; + config.sops.templates."prometheus-plex-media-server-exporter/secrets".path; openFirewall = true; }; }