vtcode_core/cli/
tool_policy_commands.rs1use crate::tool_policy::{ToolPolicy, ToolPolicyManager};
4use crate::tools::ToolRegistry;
5use crate::utils::colors::style;
6use anyhow::Result;
7use clap::Subcommand;
8
9#[derive(Debug, Clone, Subcommand)]
11pub enum ToolPolicyCommands {
12 Status,
14 Allow {
16 tool: String,
18 },
19 Deny {
21 tool: String,
23 },
24 Prompt {
26 tool: String,
28 },
29 AllowAll,
31 DenyAll,
33 ResetAll,
35}
36
37pub async fn handle_tool_policy_command(command: ToolPolicyCommands) -> Result<()> {
39 let mut policy_manager = ToolPolicyManager::new().await?;
40
41 match command {
42 ToolPolicyCommands::Status => {
43 policy_manager.print_status();
44 }
45 ToolPolicyCommands::Allow { tool } => {
46 let normalized_tool = normalize_cli_tool_name(&tool).await;
47 policy_manager.set_policy(&normalized_tool, ToolPolicy::Allow).await?;
48 println!(
49 "{}",
50 style(format!("✓ Tool '{}' is now allowed", display_tool_name(&tool, &normalized_tool))).green()
51 );
52 }
53 ToolPolicyCommands::Deny { tool } => {
54 let normalized_tool = normalize_cli_tool_name(&tool).await;
55 policy_manager.set_policy(&normalized_tool, ToolPolicy::Deny).await?;
56 println!(
57 "{}",
58 style(format!("✗ Tool '{}' is now denied", display_tool_name(&tool, &normalized_tool))).red()
59 );
60 }
61 ToolPolicyCommands::Prompt { tool } => {
62 let normalized_tool = normalize_cli_tool_name(&tool).await;
63 policy_manager.set_policy(&normalized_tool, ToolPolicy::Prompt).await?;
64 println!(
65 "{}",
66 style(format!(
67 "? Tool '{}' will now prompt for confirmation",
68 display_tool_name(&tool, &normalized_tool)
69 ))
70 .cyan()
71 );
72 }
73 ToolPolicyCommands::AllowAll => {
74 policy_manager.allow_all_tools().await?;
75 println!("{}", style("✓ All tools are now allowed").green());
76 }
77 ToolPolicyCommands::DenyAll => {
78 policy_manager.deny_all_tools().await?;
79 println!("{}", style("✗ All tools are now denied").red());
80 }
81 ToolPolicyCommands::ResetAll => {
82 policy_manager.reset_all_to_prompt().await?;
83 println!("{}", style("? All tools reset to prompt for confirmation").cyan());
84 }
85 }
86
87 Ok(())
88}
89
90async fn normalize_cli_tool_name(tool: &str) -> String {
91 let Ok(workspace_root) = std::env::current_dir() else {
92 return tool.to_string();
93 };
94
95 let registry = ToolRegistry::new(workspace_root).await;
96 registry
97 .resolve_public_tool_name_sync(tool)
98 .unwrap_or_else(|_| tool.to_string())
99}
100
101fn display_tool_name(requested_tool: &str, normalized_tool: &str) -> String {
102 if requested_tool == normalized_tool {
103 requested_tool.to_string()
104 } else {
105 format!("{requested_tool} -> {normalized_tool}")
106 }
107}