vinxen_git/
branch.rs

1use crate::Result;
2use git2::Repository;
3use serde::{Deserialize, Serialize};
4
5#[derive(Debug, Clone, Serialize, Deserialize)]
6pub struct BranchInfo {
7    pub name: String,
8    pub is_current: bool,
9    pub upstream: Option<String>,
10    pub commit_id: Option<String>,
11}
12
13impl BranchInfo {
14    pub fn current(repo: &Repository) -> Result<Option<Self>> {
15        let head = match repo.head() {
16            Ok(h) => h,
17            Err(_) => return Ok(None),
18        };
19
20        if head.is_branch() {
21            let name = head
22                .name()
23                .map(|n| n.strip_prefix("refs/heads/").unwrap_or(n).to_string())
24                .unwrap_or_else(|| "HEAD".to_string());
25
26            let commit_id = head.peel_to_commit().ok().map(|c| c.id().to_string());
27
28            return Ok(Some(Self {
29                name,
30                is_current: true,
31                upstream: None,
32                commit_id,
33            }));
34        }
35
36        Ok(None)
37    }
38
39    pub fn list(repo: &Repository) -> Result<Vec<Self>> {
40        let mut branches = Vec::new();
41        let current = Self::current(repo)?;
42        let current_name = current.as_ref().map(|b| b.name.clone());
43
44        let branch_names = repo.branches(None)?;
45        for branch in branch_names.flatten() {
46            if let Ok(Some(name)) = branch.0.name() {
47                let name = name.strip_prefix("refs/heads/").unwrap_or(name).to_string();
48                let is_current = current_name.as_ref() == Some(&name);
49                let commit_id = branch
50                    .0
51                    .get()
52                    .peel_to_commit()
53                    .ok()
54                    .map(|c| c.id().to_string());
55
56                branches.push(Self {
57                    name,
58                    is_current,
59                    upstream: None,
60                    commit_id,
61                });
62            }
63        }
64
65        Ok(branches)
66    }
67}