summary refs log tree commit diff stats
path: root/src/git.rs
diff options
context:
space:
mode:
Diffstat (limited to 'src/git.rs')
-rw-r--r--src/git.rs112
1 files changed, 63 insertions, 49 deletions
diff --git a/src/git.rs b/src/git.rs
index c892306..8666aa7 100644
--- a/src/git.rs
+++ b/src/git.rs
@@ -25,9 +25,9 @@ use std::ffi::{OsStr, OsString};
 use std::fmt;
 use std::fs;
 use std::io;
+use std::mem;
 use std::path::Path;
 use std::path::PathBuf;
-//use std::process;
 use std::process::{Command, Output};
 
 use impl_trait::impl_trait;
@@ -138,11 +138,20 @@ impl_trait! {
         //     self
         // }
 
-        // impl trait Into<Result<Output, GitError>> {
-        //     fn into(self) -> Result<Output, GitError> {
-        //         todo!()
-        //     }
-        // }
+        /// Spawns the command and produces a result.
+        pub fn execute(self) -> Result<Output, GitError> {
+            let Args { inner: mut cmd, args } = self;
+            let mut args = Some(args);
+            cmd.output().map_err(|e| {
+                GitError::new(e, args.take().unwrap())
+            }).and_then(|output| {
+                if output.status.success() {
+                    Ok(output)
+                } else {
+                    Err(GitError::new(output, args.take().unwrap()))
+                }
+            })
+        }
     }
 }
 
@@ -231,13 +240,13 @@ impl_trait! {
             }
             drop(branches);
 
-            for mut repo in std::mem::take(&mut self.1) {
+            for mut repo in mem::take(&mut self.1) {
                 // TODO clean up
                 let repo_id = repo.path.file_name().unwrap().to_str().unwrap()
                     .strip_prefix("ganarchy-fetch-").unwrap()
                     .strip_suffix(".git").unwrap()
                     .to_owned();
-                for branch in std::mem::take(&mut repo.inner.pending_branches) {
+                for branch in mem::take(&mut repo.inner.pending_branches) {
                     let len = branch.len();
                     let fetch_head = branch + "-" + &repo_id;
                     let branch = &fetch_head[..len];
@@ -275,7 +284,7 @@ impl_trait! {
         impl trait Drop {
             fn drop(&mut self) {
                 if !std::thread::panicking() {
-                    for repo in std::mem::take(&mut self.1) {
+                    for repo in mem::take(&mut self.1) {
                         repo.delete().unwrap();
                     }
                 }
@@ -287,7 +296,10 @@ impl_trait! {
 /// Initializer operations on the `Git` struct.
 impl Git<CacheRepo> {
     /// Creates a new instance of the `Git` struct, with the path as given.
-    pub fn at_path<T: AsRef<Path>>(_: Initializer, path: T) -> Option<Git<CacheRepo>> {
+    pub fn at_path<T: AsRef<Path>>(
+        _: Initializer,
+        path: T,
+    ) -> Option<Git<CacheRepo>> {
         let path = path.as_ref();
         // using `?` for side-effects.
         let _ = path.file_name()?.to_str()?;
@@ -322,8 +334,11 @@ impl Git<CacheRepo> {
     ///
     /// If this method unwinds, the underlying git repos, if any, will not be
     /// deleted. Instead, future calls to this method will return a GitError.
-    pub fn with_work_repos<F, R>(&mut self, count: usize, f: F)
-        -> Result<R, GitError>
+    pub fn with_work_repos<F, R>(
+        &mut self,
+        count: usize,
+        f: F,
+    ) -> Result<R, GitError>
     where F: FnOnce(&mut [Git<FetchRepo>]) -> Result<R, GitError> {
         // create some Git structs
         let mut work_repos = Vec::with_capacity(count);
@@ -365,9 +380,11 @@ impl Git<CacheRepo> {
     ///
     /// Panics if this isn't a cache branch or if commit isn't
     /// a commit.
-    pub fn check_history(&self, branch: &str, commit: &str)
-        -> Result<(), GitError>
-    {
+    pub fn check_history(
+        &self,
+        branch: &str,
+        commit: &str,
+    ) -> Result<(), GitError> {
         assert!(NamePurpose::CacheBranch.is_fit(branch));
         assert!(self.is_commit_hash(commit));
         let _output = self.cmd(|args| {
@@ -390,9 +407,12 @@ impl Git<FetchRepo> {
     ///
     /// Panics if `from` starts with `-`, if
     /// `branch` isn't a cache branch, or if `from_ref` starts with `-`.
-    pub fn fetch_source(&mut self, from: &str, branch: &str, from_ref: &str)
-        -> Result<(), GitError>
-    {
+    pub fn fetch_source(
+        &mut self,
+        from: &str,
+        branch: &str,
+        from_ref: &str,
+    ) -> Result<(), GitError> {
         assert!(!from.starts_with("-"));
         assert!(!from_ref.starts_with("-"));
         assert!(NamePurpose::WorkBranch.is_fit(branch));
@@ -407,9 +427,11 @@ impl Git<FetchRepo> {
 
     /// Returns the number of commits removed and the number of added between
     /// from and to, respectively.
-    pub fn get_counts(&self, from: &str, to: &str)
-        -> Result<(u64, u64), GitError>
-    {
+    pub fn get_counts(
+        &self,
+        from: &str,
+        to: &str,
+    ) -> Result<(u64, u64), GitError> {
         // if called on a cache repo, `from` may no longer exist. the FetchRepo
         // requirement makes sure `from` has not been garbage-collected.
         assert!(self.is_commit_hash(from));
@@ -422,7 +444,7 @@ impl Git<FetchRepo> {
             args.arg("--");
         })?;
         // perf: Vec::default doesn't allocate.
-        let stdout = std::mem::take(&mut output.stdout);
+        let stdout = mem::take(&mut output.stdout);
         let stdout = String::from_utf8(stdout);
         match stdout.as_ref().ok().map(|x| x.trim()).filter(|x| {
             x.trim_start_matches(|x| {
@@ -470,7 +492,7 @@ impl<T: RepoKind> Git<T> {
             args.arg(branch);
         })?;
         // perf: Vec::default doesn't allocate.
-        let stdout = std::mem::take(&mut output.stdout);
+        let stdout = mem::take(&mut output.stdout);
         let stdout = String::from_utf8(stdout);
         match stdout.as_ref().map(|x| x.strip_prefix(branch)) {
             Ok(Some("")) | Ok(Some("\n")) | Ok(Some("\r\n")) => {
@@ -496,9 +518,7 @@ impl<T: RepoKind> Git<T> {
     /// # Panics
     ///
     /// Panics if `target` starts with `-`.
-    pub fn get_hash(&self, target: &str)
-        -> Result<String, GitError>
-    {
+    pub fn get_hash(&self, target: &str) -> Result<String, GitError> {
         assert!(!target.starts_with("-"));
         let mut output = self.cmd(|args| {
             args.arg("show");
@@ -508,7 +528,7 @@ impl<T: RepoKind> Git<T> {
             args.arg("--");
         })?;
         // perf: Vec::default doesn't allocate.
-        let stdout = std::mem::take(&mut output.stdout);
+        let stdout = mem::take(&mut output.stdout);
         let stdout = String::from_utf8(stdout);
         output.stdout = match stdout {
             Ok(mut h) if self.is_commit_hash(h.trim()) => {
@@ -534,9 +554,7 @@ impl<T: RepoKind> Git<T> {
     /// # Panics
     ///
     /// Panics if `target` starts with `-`.
-    pub fn get_message(&self, target: &str)
-        -> Result<String, GitError>
-    {
+    pub fn get_message(&self, target: &str) -> Result<String, GitError> {
         assert!(!target.starts_with("-"));
         let mut output = self.cmd(|args| {
             args.arg("show");
@@ -546,7 +564,7 @@ impl<T: RepoKind> Git<T> {
             args.arg("--");
         })?;
         // perf: Vec::default doesn't allocate.
-        let stdout = std::mem::take(&mut output.stdout);
+        let stdout = mem::take(&mut output.stdout);
         let stdout = String::from_utf8(stdout);
         output.stdout = match stdout {
             Ok(e) => return Ok(e),
@@ -566,7 +584,8 @@ impl<T: RepoKind> Git<T> {
 
 /// Private operations on a git cache repo.
 impl Git<CacheRepo> {
-    /// Fetches branch `from_branch` from work repo `from` into branch `branch`.
+    /// Fetches branch `from_branch` from work repo `from` into branch
+    /// `branch`.
     ///
     /// The fetch used is a force-fetch.
     ///
@@ -574,9 +593,12 @@ impl Git<CacheRepo> {
     ///
     /// Panics if
     /// `branch` isn't a fetch head or if `from_branch` isn't a cache branch.
-    fn fetch_work(&mut self, from: &Git<FetchRepo>, branch: &str, from_branch: &str)
-        -> Result<(), GitError>
-    {
+    fn fetch_work(
+        &mut self,
+        from: &Git<FetchRepo>,
+        branch: &str,
+        from_branch: &str,
+    ) -> Result<(), GitError> {
         assert_eq!(self.sha256, from.sha256);
         assert!(NamePurpose::CacheBranch.is_fit(from_branch));
         assert!(NamePurpose::CacheFetchHead.is_fit(branch));
@@ -594,9 +616,11 @@ impl Git<CacheRepo> {
     ///
     /// Panics if `old_name` isn't a fetch head,
     /// or if `new_name` isn't a cache branch.
-    fn replace(&mut self, old_name: &str, new_name: &str)
-        -> Result<(), GitError>
-    {
+    fn replace(
+        &mut self,
+        old_name: &str,
+        new_name: &str,
+    ) -> Result<(), GitError> {
         assert!(NamePurpose::CacheBranch.is_fit(new_name));
         assert!(NamePurpose::CacheFetchHead.is_fit(old_name));
         let _output = self.cmd(|args| {
@@ -722,17 +746,7 @@ impl<T: RepoKind> Git<T> {
         let mut cmd = Args::new_cmd("git");
         f(&mut cmd);
         // run the command and make nicer Error
-        let Args { inner: mut cmd, args } = cmd;
-        let mut args = Some(args);
-        cmd.output().map_err(|e| {
-            GitError::new(e, args.take().unwrap())
-        }).and_then(|output| {
-            if output.status.success() {
-                Ok(output)
-            } else {
-                Err(GitError::new(output, args.take().unwrap()))
-            }
-        })
+        cmd.execute()
     }
 
 }