From 2076478a4f157010e0a6b45c5da76c67a9e0833e Mon Sep 17 00:00:00 2001 From: Oliver Hamlet Date: Tue, 18 Mar 2025 21:02:36 +0000 Subject: [PATCH] Replace overwrite boolean with an enum --- cxx/src/database.rs | 18 +++++++++++++--- pyo3/src/database.rs | 18 +++++++++++++--- src/database/mod.rs | 49 ++++++++++++++++++++++++++------------------ src/lib.rs | 2 +- 4 files changed, 60 insertions(+), 27 deletions(-) diff --git a/cxx/src/database.rs b/cxx/src/database.rs index 1f684894..1b6fea2a 100644 --- a/cxx/src/database.rs +++ b/cxx/src/database.rs @@ -4,7 +4,7 @@ use std::{ }; use delegate::delegate; -use libloot::error::DatabaseLockPoisonError; +use libloot::{WriteMode, error::DatabaseLockPoisonError}; use crate::{ UnsupportedEnumValueError, VerboseError, @@ -54,10 +54,16 @@ impl Database { output_path: &str, overwrite: bool, ) -> Result<(), VerboseError> { + let write_mode = if overwrite { + WriteMode::CreateOrTruncate + } else { + WriteMode::Create + }; + self.0 .read() .map_err(|_| DatabaseLockPoisonError)? - .write_user_metadata(Path::new(output_path), overwrite) + .write_user_metadata(Path::new(output_path), write_mode) .map_err(Into::into) } @@ -66,10 +72,16 @@ impl Database { output_path: &str, overwrite: bool, ) -> Result<(), VerboseError> { + let write_mode = if overwrite { + WriteMode::CreateOrTruncate + } else { + WriteMode::Create + }; + self.0 .read() .map_err(|_| DatabaseLockPoisonError)? - .write_minimal_list(Path::new(output_path), overwrite) + .write_minimal_list(Path::new(output_path), write_mode) .map_err(Into::into) } diff --git a/pyo3/src/database.rs b/pyo3/src/database.rs index 003f9eb3..c1b30d16 100644 --- a/pyo3/src/database.rs +++ b/pyo3/src/database.rs @@ -4,7 +4,7 @@ use std::{ sync::{Arc, RwLock}, }; -use libloot::error::DatabaseLockPoisonError; +use libloot::{WriteMode, error::DatabaseLockPoisonError}; use pyo3::{ Bound, PyResult, pyclass, pymethods, types::{PyAnyMethods, PyTypeMethods}, @@ -54,10 +54,16 @@ impl Database { output_path: PathBuf, overwrite: bool, ) -> Result<(), VerboseError> { + let write_mode = if overwrite { + WriteMode::CreateOrTruncate + } else { + WriteMode::Create + }; + self.0 .read() .map_err(|_| DatabaseLockPoisonError)? - .write_user_metadata(&output_path, overwrite) + .write_user_metadata(&output_path, write_mode) .map_err(Into::into) } @@ -66,10 +72,16 @@ impl Database { output_path: PathBuf, overwrite: bool, ) -> Result<(), VerboseError> { + let write_mode = if overwrite { + WriteMode::CreateOrTruncate + } else { + WriteMode::Create + }; + self.0 .read() .map_err(|_| DatabaseLockPoisonError)? - .write_minimal_list(&output_path, overwrite) + .write_minimal_list(&output_path, write_mode) .map_err(Into::into) } diff --git a/src/database/mod.rs b/src/database/mod.rs index b1fdac90..c57d546a 100644 --- a/src/database/mod.rs +++ b/src/database/mod.rs @@ -20,6 +20,15 @@ use crate::{ }; pub use error::{ConditionEvaluationError, MetadataRetrievalError}; +/// Control behaviour when writing to files. +#[derive(Clone, Copy, Debug, Eq, PartialEq, Ord, PartialOrd, Hash)] +pub enum WriteMode { + /// Create the file if it does not exist, otherwise error. + Create, + /// Create the file if it does not exist, otherwise replace its contents. + CreateOrTruncate, +} + /// The interface through which metadata can be accessed. #[derive(Debug)] pub struct Database { @@ -85,9 +94,9 @@ impl Database { pub fn write_user_metadata( &self, output_path: &Path, - overwrite: bool, + mode: WriteMode, ) -> Result<(), WriteMetadataError> { - validate_write_path(output_path, overwrite)?; + validate_write_path(output_path, mode)?; self.userlist.save(output_path) } @@ -100,9 +109,9 @@ impl Database { pub fn write_minimal_list( &self, output_path: &Path, - overwrite: bool, + mode: WriteMode, ) -> Result<(), WriteMetadataError> { - validate_write_path(output_path, overwrite)?; + validate_write_path(output_path, mode)?; let mut doc = MetadataDocument::default(); @@ -285,13 +294,13 @@ impl Database { } } -fn validate_write_path(output_path: &Path, overwrite: bool) -> Result<(), WriteMetadataError> { +fn validate_write_path(output_path: &Path, mode: WriteMode) -> Result<(), WriteMetadataError> { if !output_path.parent().map(|p| p.exists()).unwrap_or(false) { Err(WriteMetadataError::new( output_path.into(), WriteMetadataErrorReason::ParentDirectoryNotFound, )) - } else if !overwrite && output_path.exists() { + } else if mode == WriteMode::Create && output_path.exists() { Err(WriteMetadataError::new( output_path.into(), WriteMetadataErrorReason::PathAlreadyExists, @@ -487,7 +496,7 @@ plugins: let output_path = fixture.inner.local_path.join("userlist.yaml"); database - .write_user_metadata(&output_path, false) + .write_user_metadata(&output_path, WriteMode::Create) .unwrap(); let content = std::fs::read_to_string(output_path).unwrap(); @@ -503,7 +512,7 @@ plugins: assert!( database - .write_user_metadata(&output_path, false) + .write_user_metadata(&output_path, WriteMode::Create) .is_ok() ); } @@ -516,7 +525,7 @@ plugins: assert!( database - .write_user_metadata(&output_path, true) + .write_user_metadata(&output_path, WriteMode::CreateOrTruncate) .is_ok() ); } @@ -531,7 +540,7 @@ plugins: assert!( database - .write_user_metadata(&output_path, true) + .write_user_metadata(&output_path, WriteMode::CreateOrTruncate) .is_ok() ); } @@ -544,7 +553,7 @@ plugins: assert!( database - .write_user_metadata(&output_path, false) + .write_user_metadata(&output_path, WriteMode::Create) .is_err() ); } @@ -563,7 +572,7 @@ plugins: assert!( database - .write_user_metadata(&output_path, true) + .write_user_metadata(&output_path, WriteMode::CreateOrTruncate) .is_err() ); } @@ -578,7 +587,7 @@ plugins: assert!( database - .write_user_metadata(&output_path, false) + .write_user_metadata(&output_path, WriteMode::Create) .is_err() ); } @@ -599,7 +608,7 @@ plugins: assert!( database - .write_minimal_list(&output_path, false) + .write_minimal_list(&output_path, WriteMode::Create) .is_ok() ); @@ -643,7 +652,7 @@ plugins: assert!( database - .write_minimal_list(&output_path, false) + .write_minimal_list(&output_path, WriteMode::Create) .is_ok() ); } @@ -656,7 +665,7 @@ plugins: assert!( database - .write_minimal_list(&output_path, true) + .write_minimal_list(&output_path, WriteMode::CreateOrTruncate) .is_ok() ); } @@ -671,7 +680,7 @@ plugins: assert!( database - .write_minimal_list(&output_path, true) + .write_minimal_list(&output_path, WriteMode::CreateOrTruncate) .is_ok() ); } @@ -684,7 +693,7 @@ plugins: assert!( database - .write_minimal_list(&output_path, false) + .write_minimal_list(&output_path, WriteMode::Create) .is_err() ); } @@ -703,7 +712,7 @@ plugins: assert!( database - .write_minimal_list(&output_path, true) + .write_minimal_list(&output_path, WriteMode::CreateOrTruncate) .is_err() ); } @@ -718,7 +727,7 @@ plugins: assert!( database - .write_minimal_list(&output_path, false) + .write_minimal_list(&output_path, WriteMode::Create) .is_err() ); } diff --git a/src/lib.rs b/src/lib.rs index a53caf07..d93af25f 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -10,7 +10,7 @@ mod sorting; mod tests; mod version; -pub use database::Database; +pub use database::{Database, WriteMode}; pub use game::{Game, GameType}; pub use logging::{LogLevel, set_log_level, set_logging_callback}; pub use plugin::Plugin;