Same move as grafana, and the three belong together: they derive from one switch and a store with no UI is as useless as a UI with no store. `victorialogs` is the case that shows why the option-path sweep is not enough on its own. It has **zero** references spelled `swarm.victorialogs.enable` anywhere in the tree, and four spelled through `let` aliases (`vlCfg.enable` in the collector, `cfg.enable` in its own module). A sweep for the path would have reported nothing to do and left every reader broken. Prose moved with the code rather than being left behind: the comments in swarm-required-services.nix that explained why the pair derives together now sit above the assignments that do it, instead of above the gap where they used to be.
90 lines
4.2 KiB
Nix
90 lines
4.2 KiB
Nix
# "The swarm-wide services run HERE."
|
|
#
|
|
# A swarm has one forge, one matrix, one SSO. This says this host is
|
|
# where they live, and asserts the per-service `enable`s that follow —
|
|
# the same mode-not-default shape as ./local-defaults.nix, one tier down.
|
|
#
|
|
# Only the *optional* services derive: matrix and authelia. The forge has
|
|
# no `enable` to assert, because it is not optional — it is the canonical
|
|
# store for the meta flake and every agent's config repo, so it deploys
|
|
# with hyperhive itself.
|
|
{
|
|
lib,
|
|
config,
|
|
...
|
|
}:
|
|
let
|
|
swarmCfg = config.services.hyperhive.swarm;
|
|
in
|
|
{
|
|
options.services.hyperhive.swarm.enableRequiredServices = lib.mkOption {
|
|
type = lib.types.bool;
|
|
default = false;
|
|
example = true;
|
|
description = ''
|
|
Host the swarm's shared services on this hive. The services that
|
|
exist once per swarm rather than once per hive and are *optional*
|
|
— the matrix homeserver, the SSO provider — have their `enable`
|
|
asserted from this, so a swarm's service host is declared in one
|
|
place.
|
|
|
|
The forge is swarm-wide too but has nothing to assert: it is the
|
|
canonical store for the meta flake and every agent's config repo,
|
|
so it deploys with hyperhive itself and is not optional.
|
|
|
|
`services.hyperhive.enableAllLocalDefaults` turns this on as part
|
|
of the all-on-one-box mode. Set it directly to run the swarm's
|
|
services on a host that is not otherwise all-local — a dedicated
|
|
services box with hives elsewhere is exactly that shape.
|
|
|
|
With it off, this hive is a *client* of those services: it still
|
|
configures how to reach them, it just doesn't run them.
|
|
'';
|
|
};
|
|
|
|
# Same precedence reasoning as ./local-defaults.nix: fills in for an
|
|
# operator who hasn't spoken, yields to one who has.
|
|
config.services.hyperhive.swarm = {
|
|
matrix.enable = lib.mkDefault swarmCfg.enableRequiredServices;
|
|
authelia.enable = lib.mkDefault swarmCfg.enableRequiredServices;
|
|
# The queue. Added later than the two above and missed at the time —
|
|
# this file predates the `swarm-nats` container by nine days and had
|
|
# not been revisited since, so its absence was sequence rather than
|
|
# intent. It meets the rule in the option's own description exactly:
|
|
# once per swarm, and optional.
|
|
#
|
|
# The tell that it was an omission: `local-defaults.nix` already
|
|
# derives `nats.autoGenerateCallout` from the all-local mode, so that
|
|
# mode was minting the queue's callout nkeys and then never starting
|
|
# the queue they authenticate against.
|
|
nats.enable = lib.mkDefault swarmCfg.enableRequiredServices;
|
|
|
|
# The metrics pair and the log store used to derive here too. They now
|
|
# live under `deploy.*` (below, and ./deploy.nix) because "does THIS
|
|
# host run it" is a per-host decision and `swarm.*` has to be identical
|
|
# on every host. Same switch, same rule, different attribute path.
|
|
|
|
# The collector that feeds the pair above, and the only tier holding
|
|
# the upstream credential. Same rule as the rest: once per swarm,
|
|
# optional, and a hive that is not the service host is a *client* of
|
|
# it (by name, `swarm.otel.domain`) rather than a second one.
|
|
otel.enable = lib.mkDefault swarmCfg.enableRequiredServices;
|
|
};
|
|
|
|
# The collector that feeds the pair above (note: no `swarm.` prefix,
|
|
# this is ./otel.nix's existing per-hive option).
|
|
config.services.hyperhive.otel.enable = lib.mkDefault swarmCfg.enableRequiredServices;
|
|
|
|
# The metrics pair, deriving together on purpose: a store with no UI is
|
|
# unreadable and a UI with no store is empty, so there is no sensible
|
|
# deployment that takes one and not the other from this switch. An
|
|
# operator who wants exactly one still sets it directly, which
|
|
# `mkDefault` allows.
|
|
#
|
|
# The log store derives from the same switch for the same reason as the
|
|
# rest: a hive that is not the service host is a *client* of it, not a
|
|
# second one.
|
|
config.services.hyperhive.deploy.victoriametrics = lib.mkDefault swarmCfg.enableRequiredServices;
|
|
config.services.hyperhive.deploy.victorialogs = lib.mkDefault swarmCfg.enableRequiredServices;
|
|
config.services.hyperhive.deploy.grafana = lib.mkDefault swarmCfg.enableRequiredServices;
|
|
}
|