Skip to content

feat(q_cli): support 'q mcp' subcommand via qchat forwarding #1836

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 15 commits into from
May 14, 2025
Merged
17 changes: 12 additions & 5 deletions crates/q_cli/src/cli/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -200,6 +200,12 @@ pub enum CliRootCommands {
#[arg(trailing_var_arg = true, allow_hyphen_values = true)]
args: Vec<String>,
},
/// Model Context Protocol (MCP)
Mcp {
/// Args for the MCP subcommand (passed through to `qchat mcp …`)
#[arg(trailing_var_arg = true, allow_hyphen_values = true)]
args: Vec<String>,
},
/// Inline shell completions
#[command(subcommand)]
Inline(inline::InlineSubcommand),
Expand Down Expand Up @@ -235,6 +241,7 @@ impl CliRootCommands {
CliRootCommands::Version { .. } => "version",
CliRootCommands::Dashboard => "dashboard",
CliRootCommands::Chat { .. } => "chat",
CliRootCommands::Mcp { .. } => "mcp",
CliRootCommands::Inline(_) => "inline",
}
}
Expand Down Expand Up @@ -344,15 +351,16 @@ impl Cli {
CliRootCommands::Telemetry(subcommand) => subcommand.execute().await,
CliRootCommands::Version { changelog } => Self::print_version(changelog),
CliRootCommands::Dashboard => launch_dashboard(false).await,
CliRootCommands::Chat { args } => Self::execute_chat(Some(args), true).await,
CliRootCommands::Chat { args } => Self::execute_chat("chat", Some(args), true).await,
CliRootCommands::Mcp { args } => Self::execute_chat("mcp", Some(args), true).await,
CliRootCommands::Inline(subcommand) => subcommand.execute(&cli_context).await,
},
// Root command
None => Self::execute_chat(None, true).await,
None => Self::execute_chat("chat", None, true).await,
}
}

pub async fn execute_chat(args: Option<Vec<String>>, enforce_login: bool) -> Result<ExitCode> {
pub async fn execute_chat(subcmd: &str, args: Option<Vec<String>>, enforce_login: bool) -> Result<ExitCode> {
if enforce_login {
assert_logged_in().await?;
}
Expand All @@ -369,8 +377,7 @@ impl Cli {
}

let mut cmd = tokio::process::Command::new(home_local_bin()?.join(CHAT_BINARY_NAME));
cmd.arg("chat");

cmd.arg(subcmd);
if let Some(args) = args {
cmd.args(args);
}
Expand Down
2 changes: 1 addition & 1 deletion crates/q_cli/src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,7 @@ fn main() -> Result<ExitCode> {

// Hack as clap doesn't expose a custom command help.
if subcommand.as_deref() == Some("chat") && args.any(|arg| ["--help", "-h"].contains(&arg.as_str())) {
runtime.block_on(cli::Cli::execute_chat(Some(vec!["--help".to_owned()]), true))?;
runtime.block_on(cli::Cli::execute_chat("chat", Some(vec!["--help".to_owned()]), true))?;
}

let parsed = match cli::Cli::try_parse() {
Expand Down
Loading