diff options
Diffstat (limited to 'vendor/gix-lock/src/commit.rs')
-rw-r--r-- | vendor/gix-lock/src/commit.rs | 79 |
1 files changed, 79 insertions, 0 deletions
diff --git a/vendor/gix-lock/src/commit.rs b/vendor/gix-lock/src/commit.rs new file mode 100644 index 000000000..49b2595b2 --- /dev/null +++ b/vendor/gix-lock/src/commit.rs @@ -0,0 +1,79 @@ +use std::path::PathBuf; + +use crate::{File, Marker}; + +mod error { + use std::{ + fmt, + fmt::{Debug, Display}, + }; + + /// The error returned by various [`commit(…)`][super::Marker::commit()] methods + #[derive(Debug)] + pub struct Error<T: Debug> { + /// The io error that prevented the attempt to succeed + pub error: std::io::Error, + /// The marker or file which was used in the attempt to persist it + pub instance: T, + } + + impl<T: Debug> Display for Error<T> { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + Display::fmt(&self.error, f) + } + } + + impl<T: Debug> std::error::Error for Error<T> { + fn source(&self) -> Option<&(dyn std::error::Error + 'static)> { + self.error.source() + } + } +} +pub use error::Error; + +impl Marker { + /// Commit the changes written to the previously open file and overwrite the original file atomically, returning the resource path + /// on success. + /// + /// This fails for markers which weren't created with [`File::close()`] + pub fn commit(mut self) -> Result<PathBuf, Error<Self>> { + if !self.created_from_file { + return Err(Error { + error: std::io::Error::new( + std::io::ErrorKind::Other, + "refusing to commit marker that was never opened", + ), + instance: self, + }); + } + let resource_path = self.resource_path(); + match self.inner.persist(&resource_path) { + Ok(_) => Ok(resource_path), + Err(err) => Err(Error { + error: err.error, + instance: { + self.inner = err.handle; + self + }, + }), + } + } +} + +impl File { + /// Commit the changes written to this lock file and overwrite the original file atomically, returning the resource path + /// and an open file handle on success. + pub fn commit(mut self) -> Result<(PathBuf, Option<std::fs::File>), Error<Self>> { + let resource_path = self.resource_path(); + match self.inner.persist(&resource_path) { + Ok(possibly_file) => Ok((resource_path, possibly_file)), + Err(err) => Err(Error { + error: err.error, + instance: { + self.inner = err.handle; + self + }, + }), + } + } +} |