1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
use std::ffi::OsString;
use std::fs::{self, FileType, Metadata};
use std::io::{Error, Result};
use std::path::{Path, PathBuf};
use std::sync::Arc;
use super::ReadDirSpec;
#[derive(Debug)]
pub struct DirEntry {
pub depth: usize,
pub file_name: OsString,
pub file_type: Result<FileType>,
pub metadata: Option<Result<Metadata>>,
pub content_spec: Option<Arc<ReadDirSpec>>,
pub content_error: Option<Error>,
pub parent_spec: Option<Arc<ReadDirSpec>>,
}
impl DirEntry {
pub(crate) fn new(
depth: usize,
file_name: OsString,
file_type: Result<FileType>,
metadata: Option<Result<Metadata>>,
parent_spec: Option<Arc<ReadDirSpec>>,
content_spec: Option<Arc<ReadDirSpec>>,
) -> DirEntry {
DirEntry {
depth,
file_name,
file_type,
parent_spec,
metadata,
content_spec,
content_error: None,
}
}
pub fn path(&self) -> PathBuf {
let mut path = match self.parent_spec.as_ref() {
Some(parent_spec) => parent_spec.path.to_path_buf(),
None => PathBuf::from(""),
};
path.push(&self.file_name);
path
}
pub fn parent_path(&self) -> Option<&Path> {
self
.parent_spec
.as_ref()
.map(|parent_spec| parent_spec.path.as_ref())
}
pub(crate) fn try_from(path: &Path) -> Result<DirEntry> {
let metadata = fs::metadata(path)?;
let root_name = OsString::from("/");
let file_name = path.file_name().unwrap_or(&root_name);
let parent_spec = path
.parent()
.map(|parent| Arc::new(ReadDirSpec::new(parent.to_path_buf(), 0, None)));
Ok(DirEntry::new(
0,
file_name.to_owned(),
Ok(metadata.file_type()),
Some(Ok(metadata)),
parent_spec,
None,
))
}
}