deploy: retention is the store host's decision, not the swarm's

Both retentionPeriods move to deploy.<store>.retentionPeriod. Measured
before moving: each is read exactly once, in the container definition of
the module that deploys the store, and no client hive consults either --
so they are options on the auto-deployed service rather than something
every host has to agree on.

What stays in swarm.* is what a client needs to reach the store: the
package, the name it answers on, the port. Both modules said "what stays
here is its package, domain, retention and wiring" in their options-block
comments; retention no longer does, so those say so.

Renames go in deploy.nix with the rest, so the whole move keeps one home
and one file to delete when the deprecation window closes.
This commit is contained in:
atlas 2026-08-30 16:23:48 +02:00
commit 4f4f1ec3ee
4 changed files with 60 additions and 37 deletions

View file

@ -113,7 +113,7 @@ See `retentionPeriod` below before leaving it at its default.
| Option | When you'd touch it | | Option | When you'd touch it |
|---|---| |---|---|
| `swarm.victoriametrics.retentionPeriod` | Default `5y`. Lower it once you have measured how fast this swarm actually fills a disk — the default is deliberately generous because too-short silently discards history you cannot get back. | | `deploy.victoriametrics.retentionPeriod` | Default `5y`. Lower it once you have measured how fast this swarm actually fills a disk — the default is deliberately generous because too-short silently discards history you cannot get back. |
| `swarm.grafana.oidc.role` | Default `Admin` for everyone who logs in. Lower to `Viewer`/`Editor` if the swarm grows operators who should not be able to reconfigure Grafana. | | `swarm.grafana.oidc.role` | Default `Admin` for everyone who logs in. Lower to `Viewer`/`Editor` if the swarm grows operators who should not be able to reconfigure Grafana. |
| `swarm.grafana.datasourceUrl` | Only if you front VictoriaMetrics with something else. It defaults to the store on this host, which is the only thing it can reach. | | `swarm.grafana.datasourceUrl` | Only if you front VictoriaMetrics with something else. It defaults to the store on this host, which is the only thing it can reach. |
@ -144,7 +144,7 @@ swarm.
| Option | When you'd touch it | | Option | When you'd touch it |
|---|---| |---|---|
| `swarm.victorialogs.retentionPeriod` | Default `30d`, far shorter than the metrics store's — logs are bulkier per unit of value and are usually read within days of being written. Raise it if you need to answer questions about last quarter. | | `deploy.victorialogs.retentionPeriod` | Default `30d`, far shorter than the metrics store's — logs are bulkier per unit of value and are usually read within days of being written. Raise it if you need to answer questions about last quarter. |
| `swarm.victorialogs.domain` | Only to rename it. | | `swarm.victorialogs.domain` | Only to rename it. |
| `swarm.victorialogs.port` | Only if something else on the services host already claims `9428`. | | `swarm.victorialogs.port` | Only if something else on the services host already claims `9428`. |

View file

@ -97,6 +97,19 @@ in
[ "services" "hyperhive" "swarm" "forge" "ci" "package" ] [ "services" "hyperhive" "swarm" "forge" "ci" "package" ]
[ "services" "hyperhive" "deploy" "forgejo" "ci" "package" ] [ "services" "hyperhive" "deploy" "forgejo" "ci" "package" ]
) )
# Retention is read only where the container is defined, so it is a
# decision of the host running the store rather than something the swarm
# agrees on. The two stores keep everything else — package, domain, port
# — in `swarm.*`, because a client hive needs those to reach them.
(lib.mkRenamedOptionModule
[ "services" "hyperhive" "swarm" "victoriametrics" "retentionPeriod" ]
[ "services" "hyperhive" "deploy" "victoriametrics" "retentionPeriod" ]
)
(lib.mkRenamedOptionModule
[ "services" "hyperhive" "swarm" "victorialogs" "retentionPeriod" ]
[ "services" "hyperhive" "deploy" "victorialogs" "retentionPeriod" ]
)
]; ];
# ⚠️ `deploy.forgejo` is declared in ./hive-ci.nix, not here, and it is the # ⚠️ `deploy.forgejo` is declared in ./hive-ci.nix, not here, and it is the

View file

@ -53,9 +53,9 @@ let
''; '';
in in
{ {
# `enable` moved to `services.hyperhive.deploy.victorialogs.enable` — see # What stays here is what the store IS from any hive's point of view: its
# ./deploy.nix. What stays here is what the store IS: its package, # package, the name it answers on, the port. `enable` and `retentionPeriod`
# domain, retention and wiring. # are decisions of the host that runs it and live under `deploy.*`.
options.services.hyperhive.swarm.victorialogs = { options.services.hyperhive.swarm.victorialogs = {
package = lib.mkOption { package = lib.mkOption {
type = lib.types.package; type = lib.types.package;
@ -106,7 +106,14 @@ in
''; '';
}; };
retentionPeriod = lib.mkOption { };
# Retention is a property of the store this host runs, not something the
# swarm has to agree on: it is read only where the container is defined,
# and a hive that is a *client* of the log store never consults it. That
# makes it a `deploy.*` value by the same rule as the seal on the secret
# store — options on the auto-deployed service itself.
options.services.hyperhive.deploy.victorialogs.retentionPeriod = lib.mkOption {
type = lib.types.str; type = lib.types.str;
default = "30d"; default = "30d";
example = "90d"; example = "90d";
@ -119,7 +126,6 @@ in
incident"; a metric answers "is this worse than last quarter". incident"; a metric answers "is this worse than last quarter".
''; '';
}; };
};
config = lib.mkIf (hyperhiveCfg.enable && deployCfg.victorialogs.enable) { config = lib.mkIf (hyperhiveCfg.enable && deployCfg.victorialogs.enable) {
# This store publishes its own health as prometheus metrics on the same # This store publishes its own health as prometheus metrics on the same
@ -235,7 +241,7 @@ in
# boundary. # boundary.
listenAddress = "127.0.0.1:${toString cfg.port}"; listenAddress = "127.0.0.1:${toString cfg.port}";
extraOptions = [ "-retentionPeriod=${cfg.retentionPeriod}" ]; extraOptions = [ "-retentionPeriod=${deployCfg.victorialogs.retentionPeriod}" ];
}; };
}; };
}; };

View file

@ -29,9 +29,9 @@ let
domainBase = if swarmDomain == null then "invalid" else swarmDomain; domainBase = if swarmDomain == null then "invalid" else swarmDomain;
in in
{ {
# `enable` moved to `services.hyperhive.deploy.victoriametrics.enable` — see # What stays here is what the store IS from any hive's point of view: its
# ./deploy.nix. What stays here is what the store IS: its package, # package, the name it answers on, the port. `enable` and `retentionPeriod`
# domain, retention and wiring. # are decisions of the host that runs it and live under `deploy.*`.
options.services.hyperhive.swarm.victoriametrics = { options.services.hyperhive.swarm.victoriametrics = {
package = lib.mkOption { package = lib.mkOption {
type = lib.types.package; type = lib.types.package;
@ -73,7 +73,12 @@ in
''; '';
}; };
retentionPeriod = lib.mkOption { };
# Retention is a property of the store this host runs, not something the
# swarm has to agree on: it is read only where the container is defined,
# and a hive that is a *client* of the metrics store never consults it.
options.services.hyperhive.deploy.victoriametrics.retentionPeriod = lib.mkOption {
type = lib.types.str; type = lib.types.str;
default = "5y"; default = "5y";
example = "90d"; example = "90d";
@ -88,7 +93,6 @@ in
actually accumulates data. actually accumulates data.
''; '';
}; };
};
config = lib.mkIf (hyperhiveCfg.enable && deployCfg.victoriametrics.enable) { config = lib.mkIf (hyperhiveCfg.enable && deployCfg.victoriametrics.enable) {
# The gateway name and the quick-link, both inside `deployCfg.victoriametrics.enable` — that # The gateway name and the quick-link, both inside `deployCfg.victoriametrics.enable` — that
@ -165,7 +169,7 @@ in
services.victoriametrics = { services.victoriametrics = {
enable = true; enable = true;
package = cfg.package; package = cfg.package;
retentionPeriod = cfg.retentionPeriod; retentionPeriod = deployCfg.victoriametrics.retentionPeriod;
# ⚠️ PINNED TO LOOPBACK, and this is a correction rather than a # ⚠️ PINNED TO LOOPBACK, and this is a correction rather than a
# preference: upstream's default is `:8428`, i.e. every # preference: upstream's default is `:8428`, i.e. every