pxar: extract PxarExtractOptions
same as PxarCreateOptions, but for extraction/restore rather than create. Signed-off-by: Fabian Grünbichler <f.gruenbichler@proxmox.com>
This commit is contained in:
parent
77486a608e
commit
72064fd0df
@ -1354,20 +1354,24 @@ async fn restore(param: Value) -> Result<Value, Error> {
|
|||||||
|
|
||||||
let mut reader = BufferedDynamicReader::new(index, chunk_reader);
|
let mut reader = BufferedDynamicReader::new(index, chunk_reader);
|
||||||
|
|
||||||
|
let options = proxmox_backup::pxar::PxarExtractOptions {
|
||||||
|
match_list: &[],
|
||||||
|
extract_match_default: true,
|
||||||
|
allow_existing_dirs,
|
||||||
|
on_error: None,
|
||||||
|
};
|
||||||
|
|
||||||
if let Some(target) = target {
|
if let Some(target) = target {
|
||||||
proxmox_backup::pxar::extract_archive(
|
proxmox_backup::pxar::extract_archive(
|
||||||
pxar::decoder::Decoder::from_std(reader)?,
|
pxar::decoder::Decoder::from_std(reader)?,
|
||||||
Path::new(target),
|
Path::new(target),
|
||||||
&[],
|
|
||||||
true,
|
|
||||||
proxmox_backup::pxar::Flags::DEFAULT,
|
proxmox_backup::pxar::Flags::DEFAULT,
|
||||||
allow_existing_dirs,
|
|
||||||
|path| {
|
|path| {
|
||||||
if verbose {
|
if verbose {
|
||||||
println!("{:?}", path);
|
println!("{:?}", path);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
None,
|
options,
|
||||||
)
|
)
|
||||||
.map_err(|err| format_err!("error extracting archive - {}", err))?;
|
.map_err(|err| format_err!("error extracting archive - {}", err))?;
|
||||||
} else {
|
} else {
|
||||||
|
@ -17,31 +17,26 @@ use proxmox::api::cli::*;
|
|||||||
use proxmox::api::api;
|
use proxmox::api::api;
|
||||||
|
|
||||||
use proxmox_backup::tools;
|
use proxmox_backup::tools;
|
||||||
use proxmox_backup::pxar::{fuse, format_single_line_entry, ENCODER_MAX_ENTRIES, ErrorHandler, Flags};
|
use proxmox_backup::pxar::{fuse, format_single_line_entry, ENCODER_MAX_ENTRIES, Flags, PxarExtractOptions};
|
||||||
|
|
||||||
fn extract_archive_from_reader<R: std::io::Read>(
|
fn extract_archive_from_reader<R: std::io::Read>(
|
||||||
reader: &mut R,
|
reader: &mut R,
|
||||||
target: &str,
|
target: &str,
|
||||||
feature_flags: Flags,
|
feature_flags: Flags,
|
||||||
allow_existing_dirs: bool,
|
|
||||||
verbose: bool,
|
verbose: bool,
|
||||||
match_list: &[MatchEntry],
|
options: PxarExtractOptions,
|
||||||
extract_match_default: bool,
|
|
||||||
on_error: Option<ErrorHandler>,
|
|
||||||
) -> Result<(), Error> {
|
) -> Result<(), Error> {
|
||||||
|
|
||||||
proxmox_backup::pxar::extract_archive(
|
proxmox_backup::pxar::extract_archive(
|
||||||
pxar::decoder::Decoder::from_std(reader)?,
|
pxar::decoder::Decoder::from_std(reader)?,
|
||||||
Path::new(target),
|
Path::new(target),
|
||||||
&match_list,
|
|
||||||
extract_match_default,
|
|
||||||
feature_flags,
|
feature_flags,
|
||||||
allow_existing_dirs,
|
|
||||||
|path| {
|
|path| {
|
||||||
if verbose {
|
if verbose {
|
||||||
println!("{:?}", path);
|
println!("{:?}", path);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
on_error,
|
options,
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -190,6 +185,13 @@ fn extract_archive(
|
|||||||
}) as Box<dyn FnMut(Error) -> Result<(), Error> + Send>)
|
}) as Box<dyn FnMut(Error) -> Result<(), Error> + Send>)
|
||||||
};
|
};
|
||||||
|
|
||||||
|
let options = PxarExtractOptions {
|
||||||
|
match_list: &match_list,
|
||||||
|
allow_existing_dirs,
|
||||||
|
extract_match_default,
|
||||||
|
on_error,
|
||||||
|
};
|
||||||
|
|
||||||
if archive == "-" {
|
if archive == "-" {
|
||||||
let stdin = std::io::stdin();
|
let stdin = std::io::stdin();
|
||||||
let mut reader = stdin.lock();
|
let mut reader = stdin.lock();
|
||||||
@ -197,11 +199,8 @@ fn extract_archive(
|
|||||||
&mut reader,
|
&mut reader,
|
||||||
&target,
|
&target,
|
||||||
feature_flags,
|
feature_flags,
|
||||||
allow_existing_dirs,
|
|
||||||
verbose,
|
verbose,
|
||||||
&match_list,
|
options,
|
||||||
extract_match_default,
|
|
||||||
on_error,
|
|
||||||
)?;
|
)?;
|
||||||
} else {
|
} else {
|
||||||
if verbose {
|
if verbose {
|
||||||
@ -213,11 +212,8 @@ fn extract_archive(
|
|||||||
&mut reader,
|
&mut reader,
|
||||||
&target,
|
&target,
|
||||||
feature_flags,
|
feature_flags,
|
||||||
allow_existing_dirs,
|
|
||||||
verbose,
|
verbose,
|
||||||
&match_list,
|
options,
|
||||||
extract_match_default,
|
|
||||||
on_error,
|
|
||||||
)?;
|
)?;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -297,6 +293,7 @@ fn extract_archive(
|
|||||||
},
|
},
|
||||||
)]
|
)]
|
||||||
/// Create a new .pxar archive.
|
/// Create a new .pxar archive.
|
||||||
|
#[allow(clippy::too_many_arguments)]
|
||||||
fn create_archive(
|
fn create_archive(
|
||||||
archive: String,
|
archive: String,
|
||||||
source: String,
|
source: String,
|
||||||
|
@ -24,17 +24,21 @@ use crate::pxar::dir_stack::PxarDirStack;
|
|||||||
use crate::pxar::metadata;
|
use crate::pxar::metadata;
|
||||||
use crate::pxar::Flags;
|
use crate::pxar::Flags;
|
||||||
|
|
||||||
|
pub struct PxarExtractOptions<'a> {
|
||||||
|
pub match_list: &'a[MatchEntry],
|
||||||
|
pub extract_match_default: bool,
|
||||||
|
pub allow_existing_dirs: bool,
|
||||||
|
pub on_error: Option<ErrorHandler>,
|
||||||
|
}
|
||||||
|
|
||||||
pub type ErrorHandler = Box<dyn FnMut(Error) -> Result<(), Error> + Send>;
|
pub type ErrorHandler = Box<dyn FnMut(Error) -> Result<(), Error> + Send>;
|
||||||
|
|
||||||
pub fn extract_archive<T, F>(
|
pub fn extract_archive<T, F>(
|
||||||
mut decoder: pxar::decoder::Decoder<T>,
|
mut decoder: pxar::decoder::Decoder<T>,
|
||||||
destination: &Path,
|
destination: &Path,
|
||||||
match_list: &[MatchEntry],
|
|
||||||
extract_match_default: bool,
|
|
||||||
feature_flags: Flags,
|
feature_flags: Flags,
|
||||||
allow_existing_dirs: bool,
|
|
||||||
mut callback: F,
|
mut callback: F,
|
||||||
on_error: Option<ErrorHandler>,
|
options: PxarExtractOptions,
|
||||||
) -> Result<(), Error>
|
) -> Result<(), Error>
|
||||||
where
|
where
|
||||||
T: pxar::decoder::SeqRead,
|
T: pxar::decoder::SeqRead,
|
||||||
@ -69,17 +73,17 @@ where
|
|||||||
let mut extractor = Extractor::new(
|
let mut extractor = Extractor::new(
|
||||||
dir,
|
dir,
|
||||||
root.metadata().clone(),
|
root.metadata().clone(),
|
||||||
allow_existing_dirs,
|
options.allow_existing_dirs,
|
||||||
feature_flags,
|
feature_flags,
|
||||||
);
|
);
|
||||||
|
|
||||||
if let Some(on_error) = on_error {
|
if let Some(on_error) = options.on_error {
|
||||||
extractor.on_error(on_error);
|
extractor.on_error(on_error);
|
||||||
}
|
}
|
||||||
|
|
||||||
let mut match_stack = Vec::new();
|
let mut match_stack = Vec::new();
|
||||||
let mut err_path_stack = vec![OsString::from("/")];
|
let mut err_path_stack = vec![OsString::from("/")];
|
||||||
let mut current_match = extract_match_default;
|
let mut current_match = options.extract_match_default;
|
||||||
while let Some(entry) = decoder.next() {
|
while let Some(entry) = decoder.next() {
|
||||||
use pxar::EntryKind;
|
use pxar::EntryKind;
|
||||||
|
|
||||||
@ -99,7 +103,7 @@ where
|
|||||||
|
|
||||||
extractor.set_path(entry.path().as_os_str().to_owned());
|
extractor.set_path(entry.path().as_os_str().to_owned());
|
||||||
|
|
||||||
let match_result = match_list.matches(
|
let match_result = options.match_list.matches(
|
||||||
entry.path().as_os_str().as_bytes(),
|
entry.path().as_os_str().as_bytes(),
|
||||||
Some(metadata.file_type() as u32),
|
Some(metadata.file_type() as u32),
|
||||||
);
|
);
|
||||||
|
@ -59,7 +59,7 @@ mod flags;
|
|||||||
pub use flags::Flags;
|
pub use flags::Flags;
|
||||||
|
|
||||||
pub use create::{create_archive, PxarCreateOptions};
|
pub use create::{create_archive, PxarCreateOptions};
|
||||||
pub use extract::{extract_archive, ErrorHandler};
|
pub use extract::{extract_archive, ErrorHandler, PxarExtractOptions};
|
||||||
|
|
||||||
/// The format requires to build sorted directory lookup tables in
|
/// The format requires to build sorted directory lookup tables in
|
||||||
/// memory, so we restrict the number of allowed entries to limit
|
/// memory, so we restrict the number of allowed entries to limit
|
||||||
|
Loading…
Reference in New Issue
Block a user