file-restore: Add 'v' (Virtual) ArchiveEntry type

For the actual partitions and blockdevices in a backup, which the
user sees like folders in the file-restore ui

Encoded as "None", to avoid cluttering DirEntryAttribute, where it
wouldn't make any sense to have.

Signed-off-by: Stefan Reiter <s.reiter@proxmox.com>
Signed-off-by: Thomas Lamprecht <t.lamprecht@proxmox.com>
This commit is contained in:
Stefan Reiter 2021-04-21 15:18:08 +02:00 committed by Thomas Lamprecht
parent 1011fb552b
commit 4d0dc29951
4 changed files with 21 additions and 12 deletions

View File

@ -48,7 +48,7 @@ pub fn list_dir_content<R: Read + Seek>(
let mut components = path.clone(); let mut components = path.clone();
components.push(b'/'); components.push(b'/');
components.extend(&direntry.name); components.extend(&direntry.name);
let mut entry = ArchiveEntry::new(&components, &direntry.attr); let mut entry = ArchiveEntry::new(&components, Some(&direntry.attr));
if let DirEntryAttribute::File { size, mtime } = direntry.attr { if let DirEntryAttribute::File { size, mtime } = direntry.attr {
entry.size = size.into(); entry.size = size.into();
entry.mtime = mtime.into(); entry.mtime = mtime.into();

View File

@ -1354,19 +1354,22 @@ pub struct ArchiveEntry {
} }
impl ArchiveEntry { impl ArchiveEntry {
pub fn new(filepath: &[u8], entry_type: &DirEntryAttribute) -> Self { pub fn new(filepath: &[u8], entry_type: Option<&DirEntryAttribute>) -> Self {
Self { Self {
filepath: base64::encode(filepath), filepath: base64::encode(filepath),
text: String::from_utf8_lossy(filepath.split(|x| *x == b'/').last().unwrap()) text: String::from_utf8_lossy(filepath.split(|x| *x == b'/').last().unwrap())
.to_string(), .to_string(),
entry_type: CatalogEntryType::from(entry_type).to_string(), entry_type: match entry_type {
leaf: !matches!(entry_type, DirEntryAttribute::Directory { .. }), Some(entry_type) => CatalogEntryType::from(entry_type).to_string(),
None => "v".to_owned(),
},
leaf: !matches!(entry_type, None | Some(DirEntryAttribute::Directory { .. })),
size: match entry_type { size: match entry_type {
DirEntryAttribute::File { size, .. } => Some(*size), Some(DirEntryAttribute::File { size, .. }) => Some(*size),
_ => None _ => None
}, },
mtime: match entry_type { mtime: match entry_type {
DirEntryAttribute::File { mtime, .. } => Some(*mtime), Some(DirEntryAttribute::File { mtime, .. }) => Some(*mtime),
_ => None _ => None
}, },
} }

View File

@ -174,8 +174,13 @@ async fn list(
continue; continue;
} }
let path = format!("/{}", file.filename); let path = format!("/{}", file.filename);
let attr = DirEntryAttribute::Directory { start: 0 }; let attr = if file.filename.ends_with(".pxar.didx") {
entries.push(ArchiveEntry::new(path.as_bytes(), &attr)); // a pxar file is a file archive, so it's root is also a directory root
Some(&DirEntryAttribute::Directory { start: 0 })
} else {
None
};
entries.push(ArchiveEntry::new(path.as_bytes(), attr));
} }
Ok(entries) Ok(entries)

View File

@ -148,7 +148,7 @@ fn list(
match root_entry { match root_entry {
DirEntryAttribute::File { .. } => { DirEntryAttribute::File { .. } => {
// list on file, return details // list on file, return details
res.push(ArchiveEntry::new(&param_path, &root_entry)); res.push(ArchiveEntry::new(&param_path, Some(&root_entry)));
} }
DirEntryAttribute::Directory { .. } => { DirEntryAttribute::Directory { .. } => {
// list on directory, return all contained files/dirs // list on directory, return all contained files/dirs
@ -176,7 +176,7 @@ fn list(
if let Ok(entry) = entry { if let Ok(entry) = entry {
res.push(ArchiveEntry::new( res.push(ArchiveEntry::new(
full_path.as_os_str().as_bytes(), full_path.as_os_str().as_bytes(),
&entry, Some(&entry),
)); ));
} }
} }
@ -192,7 +192,7 @@ fn list(
t_path.extend(t.as_bytes()); t_path.extend(t.as_bytes());
res.push(ArchiveEntry::new( res.push(ArchiveEntry::new(
&t_path[..], &t_path[..],
&DirEntryAttribute::Directory { start: 0 }, None,
)); ));
} }
} }
@ -203,7 +203,8 @@ fn list(
c_path.extend(c.as_bytes()); c_path.extend(c.as_bytes());
res.push(ArchiveEntry::new( res.push(ArchiveEntry::new(
&c_path[..], &c_path[..],
&DirEntryAttribute::Directory { start: 0 }, // this marks the beginning of a filesystem, i.e. '/', so this is a Directory
Some(&DirEntryAttribute::Directory { start: 0 }),
)); ));
} }
} }