soma_codemode/git/
provider.rs1use serde_json::{json, Value};
2
3use crate::ToolError;
4
5use super::command::GitCommand;
6use super::safety::validate_ref;
7
8#[derive(Debug, Clone)]
9pub struct GitProvider {
10 cwd: std::path::PathBuf,
11}
12
13impl GitProvider {
14 pub fn new(cwd: impl Into<std::path::PathBuf>) -> Self {
15 Self { cwd: cwd.into() }
16 }
17
18 pub async fn dispatch(&self, method: &str, params: Value) -> Result<Value, ToolError> {
19 match method {
20 "status" => Ok(json!({
21 "stdout": GitCommand::new(&self.cwd, ["status", "--short"]).run().await?
22 })),
23 "show_ref" => {
24 let reference = params.get("ref").and_then(Value::as_str).ok_or_else(|| {
25 ToolError::MissingParam {
26 message: "missing `ref`".to_string(),
27 param: "ref".to_string(),
28 }
29 })?;
30 validate_ref(reference)?;
31 let resolved = GitCommand::new(
32 &self.cwd,
33 vec![
34 "rev-parse".to_string(),
35 "--verify".to_string(),
36 "--quiet".to_string(),
37 format!("{reference}^{{object}}"),
38 ],
39 )
40 .run()
41 .await?;
42 Ok(json!({"ref": reference, "oid": resolved.trim()}))
43 }
44 _ => Err(ToolError::UnknownAction {
45 message: format!("unknown git method `{method}`"),
46 valid: vec!["status".to_string(), "show_ref".to_string()],
47 hint: None,
48 }),
49 }
50 }
51}