Bake the channel manifest's closure instead of a pinned app version

Production builds failed CI's baseline preflight because flake.nix pinned
the app to tag 1.8 (channel.appVersion = "1.8") while the published
manifest had moved on to 1.9.

Stop pinning the app anywhere. flake.nix now fetches the channel's
published manifest at eval time (builtins.fetchurl) and bakes its
storePath verbatim, so every image carries exactly the closure RadiantWave
published to Attic and never compiles the app from source.

- flake.nix: drop the radiantwave/radiantwave-dev inputs, appInput,
  appVersion, channelVersion and baselineOutPaths; add channelAtticUrl,
  channelManifestDir and publishedApp; builders consume the published path.
- configuration.nix: wrap the published store path in a symlinkJoin so it
  can live in environment.systemPackages; add --impure to autoUpgrade
  flags and set tarball-ttl = 0 so eval reads the current manifest.
- radiantwave-updater.nix: baselinePackage (package) -> baselinePath (str),
  seeded from the exact manifest path.
- CI (build.yml): replace the version-equality preflight with a fail-fast
  check that the announced closure is in the channel's Attic; set
  tarball-ttl = 0.
- build-rpi.sh: pass --impure.
- AGENTS.md: document the manifest-driven baseline.
This commit is contained in:
NeilClack
2026-10-07 10:28:12 -05:00
parent d17def994f
commit d54637d249
7 changed files with 118 additions and 271 deletions
+6 -7
View File
@@ -17,19 +17,18 @@ in
description = "Attic cache URL to fetch the app closure from (fetch-only, never builds).";
};
baselinePackage = lib.mkOption {
type = lib.types.package;
description = "Copy of RadiantWave baked into the system closure, used to seed the runtime pointer before the first update.";
baselinePath = lib.mkOption {
type = lib.types.str;
description = "Store path of the RadiantWave closure baked into the system closure (from the channel manifest), used to seed the runtime pointer before the first update.";
};
};
config = lib.mkIf cfg.enable {
# Runtime pointer the login shell launches RadiantWave from. Seeded on
# first boot to the baseline copy already baked into the system closure
# (so the ISO carries it with no duplication); the updater service later
# re-points it atomically to newer closures fetched from Attic.
# first boot to the exact closure the channel manifest announced (the same
# path the updater would fetch), so no spurious first update is triggered.
systemd.tmpfiles.rules = [
"L /var/lib/radiantwave/current - - - - ${cfg.baselinePackage.outPath}"
"L /var/lib/radiantwave/current - - - - ${cfg.baselinePath}"
];
systemd.services.radiantwave-updater = {