Skip to main content

pleiades_agent_git/
commit.rs

1use std::path::{Path, PathBuf};
2use std::sync::Arc;
3
4use pleiades_agent_core::error::Error;
5use pleiades_agent_core::provider::Provider;
6use pleiades_agent_prompts::BuiltinPrompts;
7
8use crate::common::{generate_from_diff, git_diff};
9
10/// Generate conventional commit messages from staged changes.
11pub struct CommitGenerator {
12    provider: Arc<dyn Provider>,
13    model: String,
14    repository: PathBuf,
15}
16
17impl CommitGenerator {
18    pub fn new(provider: Arc<dyn Provider>, model: impl Into<String>) -> Self {
19        Self {
20            provider,
21            model: model.into(),
22            repository: PathBuf::from("."),
23        }
24    }
25
26    pub fn with_repository(mut self, repository: impl Into<PathBuf>) -> Self {
27        self.repository = repository.into();
28        self
29    }
30
31    /// Generate a commit message from `git diff --staged`.
32    pub async fn generate(&self) -> Result<String, Error> {
33        let diff = staged_diff(&self.repository).await?;
34        generate_from_diff(
35            self.provider.as_ref(),
36            &self.model,
37            BuiltinPrompts::commit_message(),
38            &diff,
39            None,
40        )
41        .await
42    }
43}
44
45pub async fn staged_diff(repository: &Path) -> Result<String, Error> {
46    git_diff(repository, &["diff", "--staged", "--no-ext-diff"]).await
47}
48
49pub async fn working_diff(repository: &Path, staged: bool) -> Result<String, Error> {
50    if staged {
51        staged_diff(repository).await
52    } else {
53        git_diff(repository, &["diff", "--no-ext-diff"]).await
54    }
55}