mirror of
https://github.com/RGBCube/uutils-coreutils
synced 2025-07-28 19:47:45 +00:00
uucore: implement backup control
Most of these changes were sourced from mv's existing backup control implementation. A later commit will update the mv utility to use this new share backup control.
This commit is contained in:
parent
da085eca98
commit
7240b12895
3 changed files with 99 additions and 0 deletions
|
@ -25,6 +25,7 @@ mod features; // feature-gated code modules
|
|||
mod mods; // core cross-platform modules
|
||||
|
||||
// * cross-platform modules
|
||||
pub use crate::mods::backup_control;
|
||||
pub use crate::mods::coreopts;
|
||||
pub use crate::mods::os;
|
||||
pub use crate::mods::panic;
|
||||
|
|
|
@ -1,5 +1,6 @@
|
|||
// mods ~ cross-platforms modules (core/bundler file)
|
||||
|
||||
pub mod backup_control;
|
||||
pub mod coreopts;
|
||||
pub mod os;
|
||||
pub mod panic;
|
||||
|
|
97
src/uucore/src/lib/mods/backup_control.rs
Normal file
97
src/uucore/src/lib/mods/backup_control.rs
Normal file
|
@ -0,0 +1,97 @@
|
|||
use std::{
|
||||
env,
|
||||
path::{Path, PathBuf},
|
||||
};
|
||||
|
||||
pub static BACKUP_CONTROL_VALUES: &[&str] = &[
|
||||
"simple", "never", "numbered", "t", "existing", "nil", "none", "off",
|
||||
];
|
||||
|
||||
pub static BACKUP_CONTROL_LONG_HELP: &str = "The backup suffix is '~', unless set with --suffix or SIMPLE_BACKUP_SUFFIX. Here are the version control values:
|
||||
|
||||
none, off
|
||||
never make backups (even if --backup is given)
|
||||
|
||||
numbered, t
|
||||
make numbered backups
|
||||
|
||||
existing, nil
|
||||
numbered if numbered backups exist, simple otherwise
|
||||
|
||||
simple, never
|
||||
always make simple backups";
|
||||
|
||||
#[derive(Debug, Clone, Copy, Eq, PartialEq)]
|
||||
pub enum BackupMode {
|
||||
NoBackup,
|
||||
SimpleBackup,
|
||||
NumberedBackup,
|
||||
ExistingBackup,
|
||||
}
|
||||
|
||||
pub fn determine_backup_suffix(supplied_suffix: Option<&str>) -> String {
|
||||
if let Some(suffix) = supplied_suffix {
|
||||
String::from(suffix)
|
||||
} else {
|
||||
env::var("SIMPLE_BACKUP_SUFFIX").unwrap_or("~".to_owned())
|
||||
}
|
||||
}
|
||||
|
||||
pub fn determine_backup_mode(backup_opt_exists: bool, backup_opt: Option<&str>) -> BackupMode {
|
||||
if backup_opt_exists {
|
||||
match backup_opt.map(String::from) {
|
||||
// default is existing, see:
|
||||
// https://www.gnu.org/software/coreutils/manual/html_node/Backup-options.html
|
||||
None => BackupMode::ExistingBackup,
|
||||
Some(mode) => match &mode[..] {
|
||||
"simple" | "never" => BackupMode::SimpleBackup,
|
||||
"numbered" | "t" => BackupMode::NumberedBackup,
|
||||
"existing" | "nil" => BackupMode::ExistingBackup,
|
||||
"none" | "off" => BackupMode::NoBackup,
|
||||
_ => panic!(), // cannot happen as it is managed by clap
|
||||
},
|
||||
}
|
||||
} else {
|
||||
BackupMode::NoBackup
|
||||
}
|
||||
}
|
||||
|
||||
pub fn get_backup_path(
|
||||
backup_mode: BackupMode,
|
||||
backup_path: &Path,
|
||||
suffix: &str,
|
||||
) -> Option<PathBuf> {
|
||||
match backup_mode {
|
||||
BackupMode::NoBackup => None,
|
||||
BackupMode::SimpleBackup => Some(simple_backup_path(backup_path, suffix)),
|
||||
BackupMode::NumberedBackup => Some(numbered_backup_path(backup_path)),
|
||||
BackupMode::ExistingBackup => Some(existing_backup_path(backup_path, suffix)),
|
||||
}
|
||||
}
|
||||
|
||||
pub fn simple_backup_path(path: &Path, suffix: &str) -> PathBuf {
|
||||
let mut p = path.to_string_lossy().into_owned();
|
||||
p.push_str(suffix);
|
||||
PathBuf::from(p)
|
||||
}
|
||||
|
||||
pub fn numbered_backup_path(path: &Path) -> PathBuf {
|
||||
for i in 1_u64.. {
|
||||
let path_str = &format!("{}.~{}~", path.to_string_lossy(), i);
|
||||
let path = Path::new(path_str);
|
||||
if !path.exists() {
|
||||
return path.to_path_buf();
|
||||
}
|
||||
}
|
||||
panic!("cannot create backup")
|
||||
}
|
||||
|
||||
pub fn existing_backup_path(path: &Path, suffix: &str) -> PathBuf {
|
||||
let test_path_str = &format!("{}.~1~", path.to_string_lossy());
|
||||
let test_path = Path::new(test_path_str);
|
||||
if test_path.exists() {
|
||||
numbered_backup_path(path)
|
||||
} else {
|
||||
simple_backup_path(path, suffix)
|
||||
}
|
||||
}
|
Loading…
Add table
Add a link
Reference in a new issue