Watch
0
0
Fork
You've already forked hyperhive
0

archetypes: create an agent from an archetype with no config repo

POST /api/agents takes an archetype the stored list holds, records it in
the new agent-archetype bucket, and queues no CreateRepo, AddRepoMember or
InitAgentConfigRepo for it. A destroy clears the key. Hives may read the
bucket.

Refs #5386
This commit is contained in:
atlas 2026-10-17 08:32:48 +02:00 • committed by mara
commit b199c83899
7 changed files with 645 additions and 37 deletions

View file

@ -583,6 +583,13 @@ impl Policy {
"$JS.API.DIRECT.GET.{}.>",
swarm_queue_client::agent_permissions::STREAM
));
// The archetype an agent was created from
// (`swarm_queue_client::agent_archetype`), read the same way and every
// key for the same reason.
subjects.push(format!(
"$JS.API.DIRECT.GET.{}.>",
swarm_queue_client::agent_archetype::STREAM
));
// The one-shot import of the grants this hive's meta repo held, sent
// as a request on this hive's own subject: the controller takes the
// hive from the subject, so one hive cannot import for another.
@ -877,6 +884,38 @@ mod tests {
}
}
/// A hive reads any agent's archetype and can change none of them, and the
/// grant reaches no other bucket.
#[test]
fn a_hive_may_read_every_agents_archetype_and_write_none() {
use swarm_queue_client::agent_archetype::{STREAM, direct_get_subject, key_subject};
let p = policy()
.permissions("hive-alpha")
.expect("a hive is admitted");
let may = |subject: &str| p.publish.iter().any(|g| covers(g, subject));
for agent in ["atlas", "iris"] {
assert!(may(&direct_get_subject(agent)), "cannot read {agent}");
}
for forbidden in [
key_subject("atlas"),
format!("$JS.API.STREAM.CREATE.{STREAM}"),
format!("$JS.API.STREAM.UPDATE.{STREAM}"),
format!("$JS.API.STREAM.DELETE.{STREAM}"),
format!("$JS.API.STREAM.PURGE.{STREAM}"),
format!("$JS.API.STREAM.MSG.DELETE.{STREAM}"),
format!("$JS.API.CONSUMER.CREATE.{STREAM}"),
] {
assert!(!may(&forbidden), "hive alpha may publish {forbidden}");
}
// Not the per-source archetype list, which only the controller reads.
assert!(!may(&format!(
"$JS.API.DIRECT.GET.KV_{0}.$KV.{0}.hyperhive",
swarm_queue_client::archetypes::BUCKET
)));
}
/// A hive reads any agent's permissions and can change none of them; an
/// agent, with the template `swarm-nats.nix` passes, reads its own key and
/// no other, and writes none.