feat(mcp): add per-server tool allowlist policy module and allowedTools config field

This commit is contained in:
2026-08-27 13:37:46 -06:00
parent ee45e42013
commit 5711432ac4
7 changed files with 831 additions and 1 deletions
+43
View File
@@ -4790,6 +4790,49 @@ mod tests {
let _ = fs::remove_dir_all(&dir);
}
#[test]
fn uninstall_mcp_preserves_allowed_tools_on_surviving_entries() {
let dir = fresh_temp_dir("uninst-mcp-allowed-tools-");
let mut store = BundleStore::load_from(dir.join("installed-bundles.yaml")).unwrap();
store
.upsert_bundle("omc", test_metadata("https://github.com/x/omc"))
.unwrap();
let mcp = dir.join("mcp.json");
write_mcp(
&mcp,
r#"{"mcpServers": {
"srv": {"type": "stdio", "command": "echo"},
"user-srv": {"type": "stdio", "command": "mine", "allowedTools": ["get_*", "list_issues"]}
}}"#,
);
let parsed: McpServersConfig =
serde_json::from_str(&fs::read_to_string(&mcp).unwrap()).unwrap();
let hash = hash_bytes(
serde_json::to_string(parsed.mcp_servers.get("srv").unwrap())
.unwrap()
.as_bytes(),
);
store
.record_mcp_servers(
"omc",
vec![mcp_server_record("srv", McpAction::Added, Some(hash))],
)
.unwrap();
let servers = store.get("omc").unwrap().mcp_servers.clone();
let summary = uninstall_mcp_entries(&mut store, "omc", &servers, &mcp, true).unwrap();
assert_eq!(summary.removed, vec!["srv"]);
let raw = fs::read_to_string(&mcp).unwrap();
assert!(raw.contains("allowedTools"));
let written: McpServersConfig = serde_json::from_str(&raw).unwrap();
assert_eq!(
written.mcp_servers.get("user-srv").unwrap().allowed_tools,
Some(vec!["get_*".to_string(), "list_issues".to_string()])
);
let _ = fs::remove_dir_all(&dir);
}
#[test]
fn uninstall_mcp_reports_referenced_secrets_without_removing_them() {
let dir = fresh_temp_dir("uninst-mcp-secrets-");