diff --git a/modules/misc/ids.nix b/modules/misc/ids.nix index 34b368593..07f087ee5 100644 --- a/modules/misc/ids.nix +++ b/modules/misc/ids.nix @@ -39,11 +39,13 @@ in ids.uids = { nixbld = lib.mkDefault 350; _prometheus-node-exporter = 534; + consul = 560; }; ids.gids = { nixbld = lib.mkDefault (if config.system.stateVersion < 5 then 30000 else 350); _prometheus-node-exporter = 534; + consul = 560; }; }; diff --git a/modules/module-list.nix b/modules/module-list.nix index 8b2215ba3..15b430533 100644 --- a/modules/module-list.nix +++ b/modules/module-list.nix @@ -61,6 +61,7 @@ ./services/buildkite-agents.nix ./services/chunkwm.nix ./services/cachix-agent.nix + ./services/consul.nix ./services/dnsmasq.nix ./services/emacs.nix ./services/eternal-terminal.nix diff --git a/modules/services/consul.nix b/modules/services/consul.nix new file mode 100644 index 000000000..cbf991456 --- /dev/null +++ b/modules/services/consul.nix @@ -0,0 +1,117 @@ +{ + config, + lib, + pkgs, + ... +}: +let + + dataDir = "/var/lib/consul"; + cfg = config.services.consul; + + configOptions = { + data_dir = dataDir; + ui_config = { + enabled = cfg.webUi; + }; + } // cfg.extraConfig; + + configFiles = [ + "/etc/consul.json" + ] ++ cfg.extraConfigFiles; +in +{ + meta.maintainers = [ lib.maintainers.mjm or "mjm" ]; + + options = { + services.consul = { + enable = lib.mkOption { + type = lib.types.bool; + default = false; + description = '' + Enables the consul daemon. + ''; + }; + + package = lib.mkPackageOption pkgs "consul" { }; + + webUi = lib.mkOption { + type = lib.types.bool; + default = false; + description = '' + Enables the web interface on the consul http port. + ''; + }; + + extraConfig = lib.mkOption { + default = { }; + type = lib.types.attrsOf lib.types.anything; + description = '' + Extra configuration options which are serialized to json and added + to the config.json file. + ''; + }; + + extraConfigFiles = lib.mkOption { + default = [ ]; + type = lib.types.listOf lib.types.str; + description = '' + Additional configuration files to pass to consul + NOTE: These will not trigger the service to be restarted when altered. + ''; + }; + }; + }; + + config = lib.mkIf cfg.enable { + users.users.consul = { + uid = config.ids.uids.consul; + gid = config.ids.gids.consul; + description = "Consul agent daemon user"; + home = dataDir; + createHome = true; + # The shell is needed for health checks + shell = "/run/current-system/sw/bin/bash"; + }; + users.groups.consul = { + gid = config.ids.gid.consul; + }; + users.knownUsers = [ "consul" ]; + users.knownGroups = [ "consul" ]; + + environment = { + etc."consul.json".text = builtins.toJSON configOptions; + # We need consul.d to exist for consul to start + etc."consul.d/dummy.json".text = "{ }"; + systemPackages = [ cfg.package ]; + }; + + launchd.daemons.consul = { + path = [ cfg.package ]; + script = lib.concatStringsSep " " ( + [ + "consul" + "agent" + "-config-dir" + "/etc/consul.d" + ] + ++ lib.concatMap (n: [ + "-config-file" + n + ]) configFiles + ); + serviceConfig = + let + logPath = "${dataDir}/consul.log"; + in + { + KeepAlive = true; + RunAtLoad = true; + StandardErrorPath = logPath; + StandardOutPath = logPath; + GroupName = "consul"; + UserName = "consul"; + }; + }; + }; +}