diff --git a/Cargo.toml b/Cargo.toml index 8913364b..0a839925 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "cargo-make" -version = "0.3.10" +version = "0.3.11" authors = ["Sagie Gur-Ari "] description = "Rust task runner and build tool." license = "Apache-2.0" diff --git a/README.md b/README.md index c2f8f1d3..c804ac92 100644 --- a/README.md +++ b/README.md @@ -425,13 +425,22 @@ In addition, cargo-make will also add few environment variables that can be help * **CARGO_MAKE** - Set to "true" to help sub processes identify they are running from cargo make. * **CARGO_MAKE_TASK** - Holds the name of the main task being executed. -* **CARGO_MAKE_CRATE_NAME** - Holds the crate name from the Cargo.toml file found in the cwd (only if file exists and value is defined). -* **CARGO_MAKE_CRATE_VERSION** - Holds the crate version from the Cargo.toml file found in the cwd (only if file exists and value is defined). -* **CARGO_MAKE_CRATE_DESCRIPTION** - Holds the crate description from the Cargo.toml file found in the cwd (only if file exists and value is defined). -* **CARGO_MAKE_CRATE_LICENSE** - Holds the crate license from the Cargo.toml file found in the cwd (only if file exists and value is defined). -* **CARGO_MAKE_CRATE_DOCUMENTATION** - Holds the crate documentation link from the Cargo.toml file found in the cwd (only if file exists and value is defined). -* **CARGO_MAKE_CRATE_HOMEPAGE** - Holds the crate homepage link from the Cargo.toml file found in the cwd (only if file exists and value is defined). -* **CARGO_MAKE_CRATE_REPOSITORY** - Holds the crate repository link from the Cargo.toml file found in the cwd (only if file exists and value is defined). + +The following environment variables will be set by cargo-make if Cargo.toml file exists and the relevant value is defined: + +* **CARGO_MAKE_CRATE_NAME** - Holds the crate name from the Cargo.toml file found in the cwd. +* **CARGO_MAKE_CRATE_VERSION** - Holds the crate version from the Cargo.toml file found in the cwd. +* **CARGO_MAKE_CRATE_DESCRIPTION** - Holds the crate description from the Cargo.toml file found in the cwd. +* **CARGO_MAKE_CRATE_LICENSE** - Holds the crate license from the Cargo.toml file found in the cwd. +* **CARGO_MAKE_CRATE_DOCUMENTATION** - Holds the crate documentation link from the Cargo.toml file found in the cwd. +* **CARGO_MAKE_CRATE_HOMEPAGE** - Holds the crate homepage link from the Cargo.toml file found in the cwd. +* **CARGO_MAKE_CRATE_REPOSITORY** - Holds the crate repository link from the Cargo.toml file found in the cwd. + +The following environment variables will be set by cargo-make if the project is part of a git repo: + +* **CARGO_MAKE_GIT_BRANCH** - The current branch name. +* **CARGO_MAKE_GIT_USER_NAME** - The user name pulled from the give config user.name key. +* **CARGO_MAKE_GIT_USER_EMAIL** - The user email pulled from the give config user.email key. ### Continuous Integration @@ -646,6 +655,7 @@ See [contributing guide](.github/CONTRIBUTING.md) | Date | Version | Description | | ----------- | ------- | ----------- | +| 2017-07-09 | v0.3.11 | cargo-make now defines env vars based on project git repo information | | 2017-07-06 | v0.3.10 | cargo-make now defines env vars based on project Cargo.toml | | 2017-07-05 | v0.3.6 | Added --cwd cli arg to enable setting working directory | | 2017-07-04 | v0.3.5 | Added clippy task | diff --git a/docs/_includes/content.md b/docs/_includes/content.md index b252033f..131c9f21 100644 --- a/docs/_includes/content.md +++ b/docs/_includes/content.md @@ -398,13 +398,22 @@ In addition, cargo-make will also add few environment variables that can be help * **CARGO_MAKE** - Set to "true" to help sub processes identify they are running from cargo make. * **CARGO_MAKE_TASK** - Holds the name of the main task being executed. -* **CARGO_MAKE_CRATE_NAME** - Holds the crate name from the Cargo.toml file found in the cwd (only if file exists and value is defined). -* **CARGO_MAKE_CRATE_VERSION** - Holds the crate version from the Cargo.toml file found in the cwd (only if file exists and value is defined). -* **CARGO_MAKE_CRATE_DESCRIPTION** - Holds the crate description from the Cargo.toml file found in the cwd (only if file exists and value is defined). -* **CARGO_MAKE_CRATE_LICENSE** - Holds the crate license from the Cargo.toml file found in the cwd (only if file exists and value is defined). -* **CARGO_MAKE_CRATE_DOCUMENTATION** - Holds the crate documentation link from the Cargo.toml file found in the cwd (only if file exists and value is defined). -* **CARGO_MAKE_CRATE_HOMEPAGE** - Holds the crate homepage link from the Cargo.toml file found in the cwd (only if file exists and value is defined). -* **CARGO_MAKE_CRATE_REPOSITORY** - Holds the crate repository link from the Cargo.toml file found in the cwd (only if file exists and value is defined). + +The following environment variables will be set by cargo-make if Cargo.toml file exists and the relevant value is defined: + +* **CARGO_MAKE_CRATE_NAME** - Holds the crate name from the Cargo.toml file found in the cwd. +* **CARGO_MAKE_CRATE_VERSION** - Holds the crate version from the Cargo.toml file found in the cwd. +* **CARGO_MAKE_CRATE_DESCRIPTION** - Holds the crate description from the Cargo.toml file found in the cwd. +* **CARGO_MAKE_CRATE_LICENSE** - Holds the crate license from the Cargo.toml file found in the cwd. +* **CARGO_MAKE_CRATE_DOCUMENTATION** - Holds the crate documentation link from the Cargo.toml file found in the cwd. +* **CARGO_MAKE_CRATE_HOMEPAGE** - Holds the crate homepage link from the Cargo.toml file found in the cwd. +* **CARGO_MAKE_CRATE_REPOSITORY** - Holds the crate repository link from the Cargo.toml file found in the cwd. + +The following environment variables will be set by cargo-make if the project is part of a git repo: + +* **CARGO_MAKE_GIT_BRANCH** - The current branch name. +* **CARGO_MAKE_GIT_USER_NAME** - The user name pulled from the give config user.name key. +* **CARGO_MAKE_GIT_USER_EMAIL** - The user email pulled from the give config user.email key. ### Continuous Integration @@ -619,6 +628,7 @@ See [contributing guide](https://github.com/sagiegurari/cargo-make/blob/master/. | Date | Version | Description | | ----------- | ------- | ----------- | +| 2017-07-09 | v0.3.11 | cargo-make now defines env vars based on project git repo information | | 2017-07-06 | v0.3.10 | cargo-make now defines env vars based on project Cargo.toml | | 2017-07-05 | v0.3.6 | Added --cwd cli arg to enable setting working directory | | 2017-07-04 | v0.3.5 | Added clippy task | diff --git a/docs/api/cargo_make/index.html b/docs/api/cargo_make/index.html index e2caa7a9..5e5c5ef1 100644 --- a/docs/api/cargo_make/index.html +++ b/docs/api/cargo_make/index.html @@ -48,7 +48,7 @@

Crate cargo_make [] - [src]

+ [src]

cargo-make

Rust task runner and build tool.
diff --git a/docs/api/src/cargo_make/environment.rs.html b/docs/api/src/cargo_make/environment.rs.html index 0f6a633d..1a1dbab2 100644 --- a/docs/api/src/cargo_make/environment.rs.html +++ b/docs/api/src/cargo_make/environment.rs.html @@ -158,6 +158,26 @@ 113 114 115 +116 +117 +118 +119 +120 +121 +122 +123 +124 +125 +126 +127 +128 +129 +130 +131 +132 +133 +134 +135

 //! # env
 //!
@@ -168,6 +188,7 @@
 #[path = "./environment_test.rs"]
 mod environment_test;
 
+use gitinfo;
 use log::Logger;
 use std::env;
 use std::fs::File;
@@ -242,6 +263,22 @@
     };
 }
 
+fn setup_env_for_git_repo(logger: &Logger) {
+    let git_info = gitinfo::load(&logger);
+
+    if git_info.branch.is_some() {
+        env::set_var("CARGO_MAKE_GIT_BRANCH", &git_info.branch.unwrap());
+    }
+
+    if git_info.user_name.is_some() {
+        env::set_var("CARGO_MAKE_GIT_USER_NAME", &git_info.user_name.unwrap());
+    }
+
+    if git_info.user_email.is_some() {
+        env::set_var("CARGO_MAKE_GIT_USER_EMAIL", &git_info.user_email.unwrap());
+    }
+}
+
 /// Sets up the env before the tasks execution.
 pub fn setup_env(
     logger: &Logger,
@@ -255,6 +292,9 @@
 
     // load crate info
     setup_env_for_crate(&logger);
+
+    // load git info
+    setup_env_for_git_repo(&logger);
 }
 
 pub fn setup_cwd(
diff --git a/docs/api/src/cargo_make/gitinfo.rs.html b/docs/api/src/cargo_make/gitinfo.rs.html
new file mode 100644
index 00000000..d1d6cc94
--- /dev/null
+++ b/docs/api/src/cargo_make/gitinfo.rs.html
@@ -0,0 +1,280 @@
+
+
+
+    
+    
+    
+    
+    
+
+    gitinfo.rs.html -- source
+
+    
+    
+    
+    
+
+    
+    
+
+
+    
+
+    
+
+    
+
+    
+
+    
 1
+ 2
+ 3
+ 4
+ 5
+ 6
+ 7
+ 8
+ 9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+
+//! # gitinfo
+//!
+//! Loads git information.
+//!
+
+#[cfg(test)]
+#[path = "./gitinfo_test.rs"]
+mod gitinfo_test;
+
+use command;
+use log::Logger;
+use std::process::Command;
+use types::GitInfo;
+
+fn load_from_git_config(
+    logger: &Logger,
+    git_info: &mut GitInfo,
+) {
+    let result = Command::new("git").arg("config").arg("--list").output();
+
+    match result {
+        Ok(output) => {
+            command::validate_exit_code(Ok(output.status), logger);
+
+            let stdout = String::from_utf8_lossy(&output.stdout);
+            let lines: Vec<&str> = stdout.split('\n').collect();
+            for mut line in lines {
+                line = line.trim();
+
+                logger.verbose::<()>("Checking: ", &[&line], None);
+
+                if line.starts_with("user.name=") {
+                    let parts: Vec<&str> = line.split('=').collect();
+                    let value = parts[1];
+                    git_info.user_name = Some(value.to_string());
+                } else if line.starts_with("user.email=") {
+                    let parts: Vec<&str> = line.split('=').collect();
+                    let value = parts[1];
+                    git_info.user_email = Some(value.to_string());
+                }
+            }
+        }
+        Err(error) => logger.info("Error while running git config --list command.: ", &[], Some(&error)),
+    };
+}
+
+fn load_branch(
+    logger: &Logger,
+    git_info: &mut GitInfo,
+) {
+    let result = Command::new("git").arg("branch").output();
+
+    match result {
+        Ok(output) => {
+            command::validate_exit_code(Ok(output.status), logger);
+
+            let stdout = String::from_utf8_lossy(&output.stdout);
+            let lines: Vec<&str> = stdout.split('\n').collect();
+            for mut line in lines {
+                line = line.trim();
+
+                logger.verbose::<()>("Checking: ", &[&line], None);
+
+                if line.starts_with("*") {
+                    let parts: Vec<&str> = line.split(' ').collect();
+                    let value = parts[1];
+                    git_info.branch = Some(value.to_string());
+                }
+            }
+        }
+        Err(error) => logger.info("Error while running git branch command.: ", &[], Some(&error)),
+    };
+}
+
+pub fn load(logger: &Logger) -> GitInfo {
+    logger.verbose::<()>("Searching for git info.", &[], None);
+
+    let mut git_info = GitInfo::new();
+
+    load_from_git_config(&logger, &mut git_info);
+    load_branch(&logger, &mut git_info);
+
+    logger.verbose("Loaded git info.", &[], Some(&git_info));
+
+    git_info
+}
+
+
+ + + + + + + + + + + + + \ No newline at end of file diff --git a/docs/api/src/cargo_make/main.rs.html b/docs/api/src/cargo_make/main.rs.html index db353c0f..e433873d 100644 --- a/docs/api/src/cargo_make/main.rs.html +++ b/docs/api/src/cargo_make/main.rs.html @@ -162,6 +162,7 @@ 117 118 119 +120
 #![deny(anonymous_parameters,
         const_err,
@@ -269,6 +270,7 @@
 mod types;
 mod log;
 mod descriptor;
+mod gitinfo;
 mod environment;
 mod command;
 mod installer;
diff --git a/docs/api/src/cargo_make/types.rs.html b/docs/api/src/cargo_make/types.rs.html
index 2184a184..45361921 100644
--- a/docs/api/src/cargo_make/types.rs.html
+++ b/docs/api/src/cargo_make/types.rs.html
@@ -405,6 +405,23 @@
 360
 361
 362
+363
+364
+365
+366
+367
+368
+369
+370
+371
+372
+373
+374
+375
+376
+377
+378
+379
 
 //! # types
 //!
@@ -768,6 +785,23 @@
     /// package info
     pub package: Option<PackageInfo>
 }
+
+#[derive(Serialize, Deserialize, Debug, Clone)]
+/// Holds git info for the given repo directory
+pub struct GitInfo {
+    /// branch name
+    pub branch: Option<String>,
+    /// user.name
+    pub user_name: Option<String>,
+    /// user.email
+    pub user_email: Option<String>
+}
+
+impl GitInfo {
+    pub fn new() -> GitInfo {
+        GitInfo { branch: None, user_name: None, user_email: None }
+    }
+}
 
diff --git a/src/environment.rs b/src/environment.rs index 0a69a23d..7727fc7d 100644 --- a/src/environment.rs +++ b/src/environment.rs @@ -7,6 +7,7 @@ #[path = "./environment_test.rs"] mod environment_test; +use gitinfo; use log::Logger; use std::env; use std::fs::File; @@ -81,6 +82,22 @@ fn setup_env_for_crate(logger: &Logger) { }; } +fn setup_env_for_git_repo(logger: &Logger) { + let git_info = gitinfo::load(&logger); + + if git_info.branch.is_some() { + env::set_var("CARGO_MAKE_GIT_BRANCH", &git_info.branch.unwrap()); + } + + if git_info.user_name.is_some() { + env::set_var("CARGO_MAKE_GIT_USER_NAME", &git_info.user_name.unwrap()); + } + + if git_info.user_email.is_some() { + env::set_var("CARGO_MAKE_GIT_USER_EMAIL", &git_info.user_email.unwrap()); + } +} + /// Sets up the env before the tasks execution. pub fn setup_env( logger: &Logger, @@ -94,6 +111,9 @@ pub fn setup_env( // load crate info setup_env_for_crate(&logger); + + // load git info + setup_env_for_git_repo(&logger); } pub fn setup_cwd( diff --git a/src/environment_test.rs b/src/environment_test.rs index d42d5d7d..ba8215dd 100644 --- a/src/environment_test.rs +++ b/src/environment_test.rs @@ -1,5 +1,6 @@ use super::*; +use gitinfo; use log; use std::{thread, time}; use std::collections::HashMap; @@ -97,3 +98,26 @@ fn setup_env_for_crate_load_toml_not_found_and_cwd() { assert_eq!(env::var("CARGO_MAKE_CRATE_HOMEPAGE").unwrap(), "https://sagiegurari.github.io/cargo-make"); assert_eq!(env::var("CARGO_MAKE_CRATE_REPOSITORY").unwrap(), "https://github.com/sagiegurari/cargo-make.git"); } + +#[test] +fn setup_env_for_git_repo_with_values() { + let logger = log::create("error"); + + let git_info = gitinfo::load(&logger); + + env::set_var("CARGO_MAKE_GIT_BRANCH", "EMPTY"); + env::set_var("CARGO_MAKE_GIT_USER_NAME", "EMPTY"); + env::set_var("CARGO_MAKE_GIT_USER_EMAIL", "EMPTY"); + + setup_env_for_git_repo(&logger); + + if git_info.branch.is_some() { + assert_eq!(env::var("CARGO_MAKE_GIT_BRANCH").unwrap(), git_info.branch.unwrap()); + } + if git_info.user_name.is_some() { + assert_eq!(env::var("CARGO_MAKE_GIT_USER_NAME").unwrap(), git_info.user_name.unwrap()); + } + if git_info.user_email.is_some() { + assert_eq!(env::var("CARGO_MAKE_GIT_USER_EMAIL").unwrap(), git_info.user_email.unwrap()); + } +} diff --git a/src/gitinfo.rs b/src/gitinfo.rs new file mode 100644 index 00000000..38fb1269 --- /dev/null +++ b/src/gitinfo.rs @@ -0,0 +1,86 @@ +//! # gitinfo +//! +//! Loads git information. +//! + +#[cfg(test)] +#[path = "./gitinfo_test.rs"] +mod gitinfo_test; + +use command; +use log::Logger; +use std::process::Command; +use types::GitInfo; + +fn load_from_git_config( + logger: &Logger, + git_info: &mut GitInfo, +) { + let result = Command::new("git").arg("config").arg("--list").output(); + + match result { + Ok(output) => { + command::validate_exit_code(Ok(output.status), logger); + + let stdout = String::from_utf8_lossy(&output.stdout); + let lines: Vec<&str> = stdout.split('\n').collect(); + for mut line in lines { + line = line.trim(); + + logger.verbose::<()>("Checking: ", &[&line], None); + + if line.starts_with("user.name=") { + let parts: Vec<&str> = line.split('=').collect(); + let value = parts[1]; + git_info.user_name = Some(value.to_string()); + } else if line.starts_with("user.email=") { + let parts: Vec<&str> = line.split('=').collect(); + let value = parts[1]; + git_info.user_email = Some(value.to_string()); + } + } + } + Err(error) => logger.info("Error while running git config --list command.: ", &[], Some(&error)), + }; +} + +fn load_branch( + logger: &Logger, + git_info: &mut GitInfo, +) { + let result = Command::new("git").arg("branch").output(); + + match result { + Ok(output) => { + command::validate_exit_code(Ok(output.status), logger); + + let stdout = String::from_utf8_lossy(&output.stdout); + let lines: Vec<&str> = stdout.split('\n').collect(); + for mut line in lines { + line = line.trim(); + + logger.verbose::<()>("Checking: ", &[&line], None); + + if line.starts_with("*") { + let parts: Vec<&str> = line.split(' ').collect(); + let value = parts[1]; + git_info.branch = Some(value.to_string()); + } + } + } + Err(error) => logger.info("Error while running git branch command.: ", &[], Some(&error)), + }; +} + +pub fn load(logger: &Logger) -> GitInfo { + logger.verbose::<()>("Searching for git info.", &[], None); + + let mut git_info = GitInfo::new(); + + load_from_git_config(&logger, &mut git_info); + load_branch(&logger, &mut git_info); + + logger.verbose("Loaded git info.", &[], Some(&git_info)); + + git_info +} diff --git a/src/gitinfo_test.rs b/src/gitinfo_test.rs new file mode 100644 index 00000000..099ebc7b --- /dev/null +++ b/src/gitinfo_test.rs @@ -0,0 +1,11 @@ +use super::*; + +use log; + +#[test] +fn load_with_values() { + let logger = log::create("error"); + let git_info = load(&logger); + + assert!(git_info.branch.is_some()); +} diff --git a/src/main.rs b/src/main.rs index a06aef99..50d3d53f 100644 --- a/src/main.rs +++ b/src/main.rs @@ -104,6 +104,7 @@ extern crate toml; mod types; mod log; mod descriptor; +mod gitinfo; mod environment; mod command; mod installer; diff --git a/src/types.rs b/src/types.rs index 6e1f0c54..8709266f 100644 --- a/src/types.rs +++ b/src/types.rs @@ -360,3 +360,20 @@ pub struct CrateInfo { /// package info pub package: Option } + +#[derive(Serialize, Deserialize, Debug, Clone)] +/// Holds git info for the given repo directory +pub struct GitInfo { + /// branch name + pub branch: Option, + /// user.name + pub user_name: Option, + /// user.email + pub user_email: Option +} + +impl GitInfo { + pub fn new() -> GitInfo { + GitInfo { branch: None, user_name: None, user_email: None } + } +} diff --git a/src/types_test.rs b/src/types_test.rs index 4beee7ed..488aaf83 100644 --- a/src/types_test.rs +++ b/src/types_test.rs @@ -519,3 +519,12 @@ fn get_normalized_task_with_override_clear_true() { assert_eq!(normalized_task.install_crate.unwrap(), "linux_crate"); } + +#[test] +fn git_info_new() { + let git_info = GitInfo::new(); + + assert!(git_info.branch.is_none()); + assert!(git_info.user_name.is_none()); + assert!(git_info.user_email.is_none()); +}