feat: add hyperhive.availableModels option for configurable model picker

Adds a per-agent hyperhive.availableModels list option (default
[ haiku sonnet opus ]) rendered into the HIVE_AVAILABLE_MODELS env var
(comma-separated) so the per-agent web UI model quick-picker lists
exactly the configured models instead of a hardcoded set. Operators set
a shared default hive-wide or narrow it per-agent.

An assertion guards that hyperhive.model is present in the list so the
picker can always offer the model the agent is actually running.
This commit is contained in:
atlas 2026-06-05 13:20:35 +02:00 committed by mara
commit e5da9654f1

View file

@ -106,6 +106,34 @@ in
'';
};
options.hyperhive.availableModels = lib.mkOption {
type = lib.types.listOf lib.types.str;
default = [
"haiku"
"sonnet"
"opus"
];
example = [
"sonnet"
"opus"
];
description = ''
Models offered in the per-agent web UI's model quick-picker. Rendered
into the `HIVE_AVAILABLE_MODELS` environment variable (comma-separated)
which the harness surfaces to the agent UI, so the picker lists exactly
these models instead of a hardcoded set.
Configure hive-wide by setting a shared default (e.g. in your
`agent-base.nix`) or per-agent to narrow the menu for example a
haiku-only agent can hide `opus` and `sonnet`. The *current* model is
still set by `hyperhive.model` and remains switchable at runtime via the
UI; this option only controls which choices the picker presents.
Values are the short model names that `claude --model` accepts:
`"haiku"`, `"sonnet"`, `"opus"` (or any future identifier).
'';
};
options.hyperhive.allowedBashPatterns = lib.mkOption {
type = lib.types.listOf lib.types.str;
default = [ ];
@ -612,6 +640,17 @@ in
assertion = config.hyperhive.model != "";
message = "hyperhive.model must not be empty (set it to e.g. \"haiku\" or \"sonnet\")";
}
# The current model must appear in the quick-picker menu, otherwise the
# UI would offer no way back to the model the agent is actually running.
{
assertion =
config.hyperhive.availableModels == [ ]
|| builtins.elem config.hyperhive.model config.hyperhive.availableModels;
message =
"hyperhive.model (\"${config.hyperhive.model}\") must be one of "
+ "hyperhive.availableModels ([ ${lib.concatStringsSep " " config.hyperhive.availableModels} ]) "
+ " add it to the list or change the model.";
}
# hyperhive.forge.url must look like an HTTP URL when non-default.
{
assertion =
@ -868,6 +907,11 @@ in
# host-level `services.hyperhive.c0re.contextWindowTokens` option — not set here.
environment.variables = {
HIVE_DEFAULT_MODEL = config.hyperhive.model;
# HIVE_AVAILABLE_MODELS is the comma-separated menu for the per-agent
# UI model quick-picker (see hyperhive.availableModels). The harness
# surfaces it to the frontend; an empty value falls back to the
# built-in default list.
HIVE_AVAILABLE_MODELS = lib.concatStringsSep "," config.hyperhive.availableModels;
HIVE_ASSETS_DIR = "${pkgs.hyperhive-assets}/share/hyperhive";
SHELL = "${pkgs.bashInteractive}/bin/bash";
}