fix(#2860): make hyperhive.forge.url required, drop the loopback default

The default `http://localhost:3000` was a guess, and a guess that
evaluates is worse than one that doesn't: the forge may run on a
different host from the agents, and inside an agent's network namespace
`localhost` reaches the agent itself, not the forge. hive-c0re renders
this option into every agent's config from the host's `HIVE_FORGE_URL`,
which `hive-c0re.nix` sets unconditionally, so nothing legitimate was
relying on the default to be there.

Also tightens the URL assertion, which accepted `""`. That escape hatch
only existed because the default made the empty case unreachable; with
the default gone, `""` is exactly what a caller supplies when they have
nothing, so it now fails naming the option instead of silently building
a config that talks to nowhere.

Refs #2860
This commit is contained in:
atlas 2026-07-31 22:53:51 +02:00
commit 7ef9905e9f

View file

@ -21,7 +21,6 @@ in
{
options.hyperhive.forge.url = lib.mkOption {
type = lib.types.str;
default = "http://localhost:3000";
example = "http://forge.internal:3000";
description = ''
Base URL of the hyperhive-managed Forgejo. Used at container
@ -31,16 +30,27 @@ in
shell out to `tea` without an extra auth dance. No-op when the
forge-token file is missing (i.e. hive-forge isn't running on
the host).
**Required, deliberately undefaulted.** hive-c0re renders it into
every agent's config from the host's `HIVE_FORGE_URL`, which
`hive-c0re.nix` sets unconditionally --- the forge is mandatory.
A loopback default would be a guess: the forge may run on a
different host from the agents, and inside an agent's network
namespace `localhost` reaches the agent, not the forge. An
unevaluatable config is better than one that builds and then
talks to the wrong machine.
'';
};
config = {
assertions = [
# hyperhive.forge.url must look like an HTTP URL when non-default.
# The empty string is the one value the type permits that cannot
# be a URL, and it is what a caller supplies when they have
# nothing --- exactly the case the removed loopback default used
# to paper over. Reject it here so the failure names the option.
{
assertion =
config.hyperhive.forge.url == ""
|| lib.hasPrefix "http://" config.hyperhive.forge.url
lib.hasPrefix "http://" config.hyperhive.forge.url
|| lib.hasPrefix "https://" config.hyperhive.forge.url;
message = "hyperhive.forge.url must be an http:// or https:// URL (got: \"${config.hyperhive.forge.url}\")";
}