diff --git a/CHANGELOG.md b/CHANGELOG.md new file mode 100644 index 0000000..5af684f --- /dev/null +++ b/CHANGELOG.md @@ -0,0 +1,63 @@ +# Changelog +All notable changes to this project will be documented in this file. + +The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/), +and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html). + +## [Unreleased] + +## [0.1.0] - 2023-08-01 + +### Added +- add docker setup +- refactor frontend configuration +- with all the way through +- with create pull request and release +- with gitea +- with prepend as well +- add cliff +- remove tokio +- with doctor +- with git client +- with fixes +- with conventional parse +- with tags command +- add semver +- can get commit chain +- with start of environment engine +- with gitea client +- fmt +- add gitea client stub +- add tests for git setup +- split headings into local and global +- rename to cuddle_please +- add config parsing +- with basic get dir +- add mkdocs +- add base + +### Other +- remove old changelog +- *(deps)* update all dependencies (#2) +- *(release)* 0.0.1 (#4) +- release command +- add cuddle.release to this repository +- add granular docker setup +- fix checks +- chck refactor commands +- move doctor command +- fmt +- rename release command +- move gitea command into its own file +- move config list +- move gitea out of the way +- move config building out of main execution loop +- move commands and misc out of main binary package +- fmt +- check hide commands +- move cuddle-please to cuddle-please release +- remove no-vcs option (moved to a later stage if github is someday adopted +- fix clippy warnings +- clippy fix +- fix +- cleanup diff --git a/README.md b/README.md index 88c751c..e375b10 100644 --- a/README.md +++ b/README.md @@ -1,17 +1,23 @@ # Cuddle Please -Cuddle Please is an extension to `cuddle`, it is a separate binary that can be executed standalone as cuddle-please, or in cuddle as `cuddle please`. +Cuddle Please is an extension to `cuddle`, it is a separate binary that can be executed standalone as `cuddle-please`, or in cuddle as `cuddle please`. The goal of the software is to be a `release-please` clone, targeting `gitea` instead of `github`. The tool can be executed as a binary using: -`cuddle please pr create` +```bash +cuddle please release # if using cuddle +# or +cuddle-please release # if using standalone +``` And when a release has been built: ```bash cuddle please release +# or +cuddle-please release ``` cuddle will default to information to it available in git, or use a specific entry in `cuddle.yaml` called @@ -28,7 +34,6 @@ or as `cuddle.please.yaml` See docs for more information about installation and some such - ## Checklist ### 0.1 Milestone @@ -36,26 +41,27 @@ See docs for more information about installation and some such - [x] Hide unneccessary commands - [x] Redo configuration frontend - [x] Refactor command.rs into smaller bits so that bits are easier to test -- [ ] Add cuddle.release.yaml to this repo -- [ ] Add reporter for PR and Repositories -- [ ] Setup temporary git name and email to use for git committing -- [ ] Add docker setup -- [ ] Add more granular tests +- [x] Add cuddle.release.yaml to this repo +- [x] Setup temporary git name and email to use for git committing ### 0.2 Milestone - [ ] Add docs -- [ ] Add asciidoc +- [ ] Add asciinema - [ ] Add examples - [ ] Fx drone config - [ ] Releaser - [ ] On main/master +- [ ] Add reporter for PR and Repositories - [ ] tbd... ### 0.3 Milestone - [ ] Add inquire for missing values when needed (when not running in ci or have a proper tty) +- [ ] Break down cuddle-please-misc ### 0.x Milestone - [ ] Add github support +- [ ] Add custom strategies - [ ] Create docker image +- [ ] Add more granular tests diff --git a/crates/cuddle-please-commands/src/command.rs b/crates/cuddle-please-commands/src/command.rs index 4645d47..3265116 100644 --- a/crates/cuddle-please-commands/src/command.rs +++ b/crates/cuddle-please-commands/src/command.rs @@ -89,7 +89,7 @@ impl Command { pub fn execute(self, current_dir: Option<&Path>) -> anyhow::Result<()> { let config = self.build_config(current_dir)?; - let git_client = self.get_git(config.get_source())?; + let git_client = self.get_git(&config)?; let gitea_client = self.get_gitea_client(&config); match &self.commands { @@ -131,11 +131,15 @@ impl Command { Ok(config) } - fn get_git(&self, current_dir: &Path) -> anyhow::Result { + fn get_git(&self, config: &PleaseConfig) -> anyhow::Result { if self.global.no_vcs { Ok(VcsClient::new_noop()) } else { - VcsClient::new_git(current_dir) + VcsClient::new_git( + config.get_source(), + config.settings.git_username.clone(), + config.settings.git_email.clone(), + ) } } diff --git a/crates/cuddle-please-frontend/src/gatheres/cli.rs b/crates/cuddle-please-frontend/src/gatheres/cli.rs index 54dec55..5632e58 100644 --- a/crates/cuddle-please-frontend/src/gatheres/cli.rs +++ b/crates/cuddle-please-frontend/src/gatheres/cli.rs @@ -52,6 +52,24 @@ pub struct ConfigArgs { help_heading = "Config" )] pub branch: Option, + + /// which git username to use for commits + #[arg( + env = "CUDDLE_PLEASE_GIT_USERNAME", + long, + global = true, + help_heading = "Config" + )] + pub git_username: Option, + + /// which git email to use for commits + #[arg( + env = "CUDDLE_PLEASE_GIT_EMAIL", + long, + global = true, + help_heading = "Config" + )] + pub git_email: Option, } impl From for PleaseConfigBuilder { @@ -65,6 +83,8 @@ impl From for PleaseConfigBuilder { }), settings: Some(PleaseSettingsConfigBuilder { api_url: value.api_url, + git_username: value.git_username, + git_email: value.git_email, }), } } diff --git a/crates/cuddle-please-frontend/src/lib.rs b/crates/cuddle-please-frontend/src/lib.rs index d66b5c6..fb55cef 100644 --- a/crates/cuddle-please-frontend/src/lib.rs +++ b/crates/cuddle-please-frontend/src/lib.rs @@ -19,6 +19,8 @@ pub struct PleaseProjectConfig { #[derive(Debug, Clone)] pub struct PleaseSettingsConfig { pub api_url: String, + pub git_username: Option, + pub git_email: Option, } #[derive(Debug, Clone)] @@ -43,6 +45,12 @@ impl PleaseConfig { pub fn get_api_url(&self) -> &str { &self.settings.api_url } + pub fn get_git_username(&self) -> Option { + self.settings.git_username.clone() + } + pub fn get_git_email(&self) -> Option { + self.settings.git_email.clone() + } } impl Display for PleaseConfig { @@ -52,6 +60,12 @@ impl Display for PleaseConfig { writeln!(f, " repository: {}", self.get_repository())?; writeln!(f, " branch: {}", self.get_branch())?; writeln!(f, " api_url: {}", self.get_api_url())?; + if let Some(git_username) = self.get_git_username() { + writeln!(f, " git_username: {}", git_username)?; + } + if let Some(git_email) = self.get_git_email() { + writeln!(f, " git_email: {}", git_email)?; + } Ok(()) } diff --git a/crates/cuddle-please-frontend/src/stage0_config.rs b/crates/cuddle-please-frontend/src/stage0_config.rs index 5bb78f8..6c8c689 100644 --- a/crates/cuddle-please-frontend/src/stage0_config.rs +++ b/crates/cuddle-please-frontend/src/stage0_config.rs @@ -15,6 +15,8 @@ pub struct PleaseProjectConfigBuilder { #[derive(Debug, Clone, Serialize, Deserialize, Default)] pub struct PleaseSettingsConfigBuilder { pub api_url: Option, + pub git_username: Option, + pub git_email: Option, } #[derive(Debug, Clone, Serialize, Deserialize, Default)] @@ -56,6 +58,13 @@ impl PleaseConfigBuilder { fsettings.api_url = Some(api_url); } + if let Some(git_username) = settings.git_username { + fsettings.git_username = Some(git_username); + } + if let Some(git_email) = settings.git_email { + fsettings.git_email = Some(git_email); + } + self.settings = Some(fsettings); } @@ -99,6 +108,8 @@ impl TryFrom for PleaseSettingsConfig { fn try_from(value: PleaseSettingsConfigBuilder) -> Result { Ok(Self { api_url: value.api_url.ok_or(value_is_missing("api_url"))?, + git_username: value.git_username.clone(), + git_email: value.git_username.clone(), }) } } diff --git a/crates/cuddle-please-misc/src/git_client.rs b/crates/cuddle-please-misc/src/git_client.rs index f3f61e9..324ffcc 100644 --- a/crates/cuddle-please-misc/src/git_client.rs +++ b/crates/cuddle-please-misc/src/git_client.rs @@ -3,7 +3,11 @@ use std::path::{Path, PathBuf}; #[derive(Clone, Debug, PartialEq)] pub enum VcsClient { Noop {}, - Git { source: PathBuf }, + Git { + source: PathBuf, + username: String, + email: String, + }, } impl VcsClient { @@ -11,13 +15,23 @@ impl VcsClient { Self::Noop {} } - pub fn new_git(path: &Path) -> anyhow::Result { + pub fn new_git( + path: &Path, + git_username: Option>, + git_email: Option>, + ) -> anyhow::Result { if !path.to_path_buf().join(".git").exists() { anyhow::bail!("git directory not found in: {}", path.display().to_string()) } Ok(Self::Git { source: path.to_path_buf(), + username: git_username + .map(|u| u.into()) + .unwrap_or("cuddle-please".to_string()), + email: git_email + .map(|e| e.into()) + .unwrap_or("bot@cuddle.sh".to_string()), }) } @@ -38,9 +52,19 @@ impl VcsClient { fn exec_git(&self, args: &[&str]) -> anyhow::Result<()> { match self { VcsClient::Noop {} => {} - VcsClient::Git { source } => { + VcsClient::Git { + source, + username, + email, + } => { let checkout_branch = std::process::Command::new("git") .current_dir(source.as_path()) + .args(&[ + "-c", + &format!("user.name={}", username), + "-c", + &format!("user.email={}", email), + ]) .args(args) .output()?; diff --git a/crates/cuddle-please/tests/git.rs b/crates/cuddle-please/tests/git.rs index f123965..953c937 100644 --- a/crates/cuddle-please/tests/git.rs +++ b/crates/cuddle-please/tests/git.rs @@ -17,7 +17,7 @@ fn exec_git_into_branch() { add_commit(tempdir.path(), "second").unwrap(); add_tag(tempdir.path(), "1.0.1").unwrap(); - let vcs = VcsClient::new_git(tempdir.path()).unwrap(); + let vcs = VcsClient::new_git(tempdir.path(), None::, None::).unwrap(); vcs.checkout_branch().unwrap(); let output = std::process::Command::new("git") @@ -48,7 +48,7 @@ fn add_files_to_commit() { add_commit(tempdir.path(), "first").unwrap(); add_tag(tempdir.path(), "1.0.0").unwrap(); - let vcs = VcsClient::new_git(tempdir.path()).unwrap(); + let vcs = VcsClient::new_git(tempdir.path(), None::, None::).unwrap(); vcs.checkout_branch().unwrap(); std::fs::File::create(tempdir.path().join("changelog")).unwrap(); @@ -76,7 +76,7 @@ fn reset_branch() { add_commit(tempdir.path(), "first").unwrap(); add_tag(tempdir.path(), "1.0.0").unwrap(); - let vcs = VcsClient::new_git(tempdir.path()).unwrap(); + let vcs = VcsClient::new_git(tempdir.path(), None::, None::).unwrap(); vcs.checkout_branch().unwrap(); std::fs::File::create(tempdir.path().join("changelog-first")).unwrap(); diff --git a/crates/cuddle-please/tests/vcs.rs b/crates/cuddle-please/tests/vcs.rs index 0575160..13265be 100644 --- a/crates/cuddle-please/tests/vcs.rs +++ b/crates/cuddle-please/tests/vcs.rs @@ -16,6 +16,13 @@ fn test_vcs_get_noop() { #[traced_test] fn test_vcs_get_git_found() { let testdata = get_test_data_path("git-found"); - let git = VcsClient::new_git(&testdata).unwrap(); - assert_eq!(git, VcsClient::Git { source: testdata }) + let git = VcsClient::new_git(&testdata, None::, None::).unwrap(); + assert_eq!( + git, + VcsClient::Git { + source: testdata, + username: "cuddle-please".into(), + email: "bot@cuddle.sh".into() + } + ) } diff --git a/cuddle.yaml b/cuddle.yaml index 646e08b..9667bde 100644 --- a/cuddle.yaml +++ b/cuddle.yaml @@ -1,6 +1,6 @@ # yaml-language-server: $schema=https://git.front.kjuulh.io/kjuulh/cuddle/raw/branch/main/schemas/base.json -base: "git@git.front.kjuulh.io:kjuulh/cuddle-base.git" +base: "git@git.front.kjuulh.io:kjuulh/cuddle-rust-cli-plan.git" vars: service: "cuddle-please"