1pub mod commit;
2pub mod error;
3
4use color_eyre::eyre::Result;
5use git2::Repository;
6use phf::phf_map;
7use regex::Regex;
8
9use crate::commit::Author;
10use crate::error::Error;
11
12lazy_static::lazy_static! {
13 pub static ref BRANCH_NAME_REGEX: Regex = Regex::new("([A-Z])-?([0-9]+).*").unwrap();
15}
16
17pub static TEAM_MAPPING: phf::Map<&'static str, &'static str> = phf_map! {
19 "A" => "ANALYTICS"
20};
21
22pub fn extract_from_branch(branch_name: &str) -> Result<(String, u32)> {
23 let captures = BRANCH_NAME_REGEX
24 .captures(branch_name)
25 .map_or(Err(Error::InvalidBranchName(branch_name.to_string())), Ok)?;
26
27 let team_name = TEAM_MAPPING
28 .get(&captures[1])
29 .map_or(Err(Error::UnknownPrefix(captures[1].to_string())), Ok)?;
30
31 let issue_number = captures[2].parse::<u32>()?;
32
33 Ok((String::from(*team_name), issue_number))
34}
35
36pub fn check_staged_changes(repository: &Repository) -> Result<()> {
37 let mut has_staged = false;
38 for status_entry in repository.statuses(None)?.iter() {
39 let status = status_entry.status();
40 has_staged |= status.is_index_deleted()
41 || status.is_index_modified()
42 || status.is_index_new()
43 || status.is_index_renamed()
44 || status.is_index_typechange();
45 if has_staged {
46 return Ok(());
47 }
48 }
49 Err(Error::NoStagedChanges)?
50}
51
52pub fn commit(repository: &Repository, message: &str) -> Result<()> {
53 let tree_oid = repository.index()?.write_tree()?;
54 let tree = repository.find_tree(tree_oid)?;
55 let parent_commit = repository.head()?.resolve()?.peel_to_commit()?;
56 let author = Author::try_from(repository)?;
57 let signature = &author.try_into()?;
58 repository.commit(
59 Some("HEAD"),
60 signature,
61 signature,
62 &message.to_string(),
63 &tree,
64 &[&parent_commit],
65 )?;
66 Ok(())
67}