swarm-controller: mint each agent's forge token and store it in bao
A MintAgentForgeToken node mints a fixed-name swarm-agent token with the admin API, keeps it when the stored value's last eight and the normalised scopes match the forge's list, and otherwise deletes and re-creates it. The token is stored at swarm/agents/<agent>/forge-token. Agent creation inserts the node, and a pass at start and every five minutes inserts it for every agent holding a store identity whose token is missing or stale. Refs #3782
This commit is contained in:
parent
2fda529ca8
commit
52c8c0b0de
7 changed files with 977 additions and 4 deletions
|
|
@ -96,6 +96,23 @@ pub fn agent_object_name(agent: &str) -> Result<String, Error> {
|
|||
Ok(format!("{AGENT_PREFIX}{agent}"))
|
||||
}
|
||||
|
||||
/// The agents among `names`, a listing of cert-auth roles: the inverse of
|
||||
/// [`agent_object_name`], for a caller that needs the set of agents holding a
|
||||
/// store identity.
|
||||
///
|
||||
/// A name that carries the prefix but whose suffix is not a legal segment is
|
||||
/// dropped rather than returned: [`agent_object_name`] could not have produced
|
||||
/// it, so it is not an agent this crate minted.
|
||||
#[must_use]
|
||||
pub fn agents_from_role_names(names: &[String]) -> Vec<String> {
|
||||
names
|
||||
.iter()
|
||||
.filter_map(|name| name.strip_prefix(AGENT_PREFIX))
|
||||
.filter(|agent| checked_segment("agent", agent).is_ok())
|
||||
.map(str::to_owned)
|
||||
.collect()
|
||||
}
|
||||
|
||||
/// One read stanza. The only shape this module emits, so "read-only" is a
|
||||
/// property of the renderer rather than of each call site.
|
||||
fn read_stanza(path: &str) -> String {
|
||||
|
|
@ -595,4 +612,33 @@ mod tests {
|
|||
let expected_queue_path = crate::queue::agent_client_path("pr1ma").expect("legal");
|
||||
assert!(p.contains(&expected_queue_path));
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn only_agent_roles_come_back_and_without_their_prefix() {
|
||||
let roles: Vec<String> = [
|
||||
"hive-agent-atlas",
|
||||
"hive-pr1ma",
|
||||
"swarm-controller",
|
||||
"hive-agent-argus",
|
||||
]
|
||||
.map(str::to_owned)
|
||||
.to_vec();
|
||||
assert_eq!(agents_from_role_names(&roles), ["atlas", "argus"]);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn a_role_agent_object_name_could_not_have_produced_is_dropped() {
|
||||
// An empty suffix and one carrying a dot are both names the prefix
|
||||
// matches and no agent can have.
|
||||
let roles: Vec<String> = ["hive-agent-", "hive-agent-a.b", "hive-agent-ok"]
|
||||
.map(str::to_owned)
|
||||
.to_vec();
|
||||
assert_eq!(agents_from_role_names(&roles), ["ok"]);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn the_listing_inverts_agent_object_name() {
|
||||
let name = agent_object_name("atlas").expect("legal");
|
||||
assert_eq!(agents_from_role_names(&[name]), ["atlas"]);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in a new issue