mirror of
https://github.com/nushell/nushell
synced 2024-12-26 13:03:07 +00:00
Add block size to du (#1341)
* Add block size to du * Change blocks to physical size * Use path instead of strings for file/directory names * Why don't I just use paths instead of strings anyway? * shorten physical size and apparent size to physical and apparent resp.
This commit is contained in:
parent
29ccb9f5cd
commit
6a371802b4
3 changed files with 52 additions and 20 deletions
10
Cargo.lock
generated
10
Cargo.lock
generated
|
@ -931,6 +931,15 @@ version = "0.1.9"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "7360491ce676a36bf9bb3c56c1aa791658183a54d2744120f27285738d90465a"
|
checksum = "7360491ce676a36bf9bb3c56c1aa791658183a54d2744120f27285738d90465a"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "filesize"
|
||||||
|
version = "0.1.0"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "3a941e39ae509cebcd46c6734c20553a9a209b92cea5fc54618fe778fea61701"
|
||||||
|
dependencies = [
|
||||||
|
"winapi 0.3.8",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "fixedbitset"
|
name = "fixedbitset"
|
||||||
version = "0.1.9"
|
version = "0.1.9"
|
||||||
|
@ -2201,6 +2210,7 @@ dependencies = [
|
||||||
"derive-new",
|
"derive-new",
|
||||||
"dirs 2.0.2",
|
"dirs 2.0.2",
|
||||||
"dunce",
|
"dunce",
|
||||||
|
"filesize",
|
||||||
"futures 0.3.3",
|
"futures 0.3.3",
|
||||||
"futures-util",
|
"futures-util",
|
||||||
"futures_codec",
|
"futures_codec",
|
||||||
|
|
|
@ -133,6 +133,7 @@ onig_sys = {version = "=69.1.0", optional = true }
|
||||||
crossterm = {version = "0.16.0", optional = true}
|
crossterm = {version = "0.16.0", optional = true}
|
||||||
url = {version = "2.1.1", optional = true}
|
url = {version = "2.1.1", optional = true}
|
||||||
semver = {version = "0.9.0", optional = true}
|
semver = {version = "0.9.0", optional = true}
|
||||||
|
filesize = "0.1.0"
|
||||||
|
|
||||||
[target.'cfg(unix)'.dependencies]
|
[target.'cfg(unix)'.dependencies]
|
||||||
users = "0.9"
|
users = "0.9"
|
||||||
|
|
|
@ -1,5 +1,8 @@
|
||||||
|
extern crate filesize;
|
||||||
|
|
||||||
use crate::commands::command::RunnablePerItemContext;
|
use crate::commands::command::RunnablePerItemContext;
|
||||||
use crate::prelude::*;
|
use crate::prelude::*;
|
||||||
|
use filesize::file_real_size_fast;
|
||||||
use glob::*;
|
use glob::*;
|
||||||
use indexmap::map::IndexMap;
|
use indexmap::map::IndexMap;
|
||||||
use nu_errors::ShellError;
|
use nu_errors::ShellError;
|
||||||
|
@ -165,32 +168,38 @@ struct DirInfo {
|
||||||
files: Vec<FileInfo>,
|
files: Vec<FileInfo>,
|
||||||
errors: Vec<ShellError>,
|
errors: Vec<ShellError>,
|
||||||
size: u64,
|
size: u64,
|
||||||
name: String,
|
blocks: u64,
|
||||||
|
path: PathBuf,
|
||||||
tag: Tag,
|
tag: Tag,
|
||||||
}
|
}
|
||||||
|
|
||||||
struct FileInfo {
|
struct FileInfo {
|
||||||
name: String,
|
path: PathBuf,
|
||||||
size: u64,
|
size: u64,
|
||||||
|
blocks: Option<u64>,
|
||||||
tag: Tag,
|
tag: Tag,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl FileInfo {
|
impl FileInfo {
|
||||||
fn new(path: impl Into<PathBuf>, deref: bool, tag: Tag) -> Result<Self, ShellError> {
|
fn new(path: impl Into<PathBuf>, deref: bool, tag: Tag) -> Result<Self, ShellError> {
|
||||||
let path = path.into();
|
let path = path.into();
|
||||||
let name = path.to_string_lossy().to_string();
|
|
||||||
let m = if deref {
|
let m = if deref {
|
||||||
std::fs::metadata(path)
|
std::fs::metadata(&path)
|
||||||
} else {
|
} else {
|
||||||
std::fs::symlink_metadata(path)
|
std::fs::symlink_metadata(&path)
|
||||||
};
|
};
|
||||||
|
|
||||||
match m {
|
match m {
|
||||||
Ok(d) => Ok(FileInfo {
|
Ok(d) => {
|
||||||
name,
|
let block_size = file_real_size_fast(&path, &d).ok();
|
||||||
|
|
||||||
|
Ok(FileInfo {
|
||||||
|
path,
|
||||||
|
blocks: block_size,
|
||||||
size: d.len(),
|
size: d.len(),
|
||||||
tag,
|
tag,
|
||||||
}),
|
})
|
||||||
|
}
|
||||||
Err(e) => Err(e.into()),
|
Err(e) => Err(e.into()),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -205,11 +214,12 @@ impl DirInfo {
|
||||||
errors: Vec::new(),
|
errors: Vec::new(),
|
||||||
files: Vec::new(),
|
files: Vec::new(),
|
||||||
size: 0,
|
size: 0,
|
||||||
|
blocks: 0,
|
||||||
tag: params.tag.clone(),
|
tag: params.tag.clone(),
|
||||||
name: path.to_string_lossy().to_string(),
|
path,
|
||||||
};
|
};
|
||||||
|
|
||||||
match std::fs::read_dir(path) {
|
match std::fs::read_dir(&s.path) {
|
||||||
Ok(d) => {
|
Ok(d) => {
|
||||||
for f in d {
|
for f in d {
|
||||||
match f {
|
match f {
|
||||||
|
@ -247,6 +257,7 @@ impl DirInfo {
|
||||||
|
|
||||||
let d = DirInfo::new(path, ¶ms, depth);
|
let d = DirInfo::new(path, ¶ms, depth);
|
||||||
self.size += d.size;
|
self.size += d.size;
|
||||||
|
self.blocks += d.blocks;
|
||||||
self.dirs.push(d);
|
self.dirs.push(d);
|
||||||
self
|
self
|
||||||
}
|
}
|
||||||
|
@ -260,6 +271,7 @@ impl DirInfo {
|
||||||
let inc = params.min.map_or(true, |s| file.size >= s);
|
let inc = params.min.map_or(true, |s| file.size >= s);
|
||||||
if inc {
|
if inc {
|
||||||
self.size += file.size;
|
self.size += file.size;
|
||||||
|
self.blocks += file.blocks.unwrap_or(0);
|
||||||
if params.all {
|
if params.all {
|
||||||
self.files.push(file);
|
self.files.push(file);
|
||||||
}
|
}
|
||||||
|
@ -286,12 +298,16 @@ impl From<DirInfo> for Value {
|
||||||
fn from(d: DirInfo) -> Self {
|
fn from(d: DirInfo) -> Self {
|
||||||
let mut r: IndexMap<String, Value> = IndexMap::new();
|
let mut r: IndexMap<String, Value> = IndexMap::new();
|
||||||
r.insert(
|
r.insert(
|
||||||
"size".to_string(),
|
"path".to_string(),
|
||||||
UntaggedValue::bytes(d.size).into_untagged_value(),
|
UntaggedValue::path(d.path).retag(d.tag.clone()),
|
||||||
);
|
);
|
||||||
r.insert(
|
r.insert(
|
||||||
"name".to_string(),
|
"apparent".to_string(),
|
||||||
UntaggedValue::string(d.name).into_untagged_value(),
|
UntaggedValue::bytes(d.size).retag(d.tag.clone()),
|
||||||
|
);
|
||||||
|
r.insert(
|
||||||
|
"physical".to_string(),
|
||||||
|
UntaggedValue::bytes(d.blocks).retag(d.tag.clone()),
|
||||||
);
|
);
|
||||||
if !d.files.is_empty() {
|
if !d.files.is_empty() {
|
||||||
let v = Value {
|
let v = Value {
|
||||||
|
@ -341,13 +357,18 @@ impl From<FileInfo> for Value {
|
||||||
fn from(f: FileInfo) -> Self {
|
fn from(f: FileInfo) -> Self {
|
||||||
let mut r: IndexMap<String, Value> = IndexMap::new();
|
let mut r: IndexMap<String, Value> = IndexMap::new();
|
||||||
r.insert(
|
r.insert(
|
||||||
"size".to_string(),
|
"path".to_string(),
|
||||||
UntaggedValue::bytes(f.size).into_untagged_value(),
|
UntaggedValue::path(f.path).retag(f.tag.clone()),
|
||||||
);
|
);
|
||||||
r.insert(
|
r.insert(
|
||||||
"name".to_string(),
|
"apparent".to_string(),
|
||||||
UntaggedValue::string(f.name).into_untagged_value(),
|
UntaggedValue::bytes(f.size).retag(f.tag.clone()),
|
||||||
);
|
);
|
||||||
|
let b = match f.blocks {
|
||||||
|
Some(k) => UntaggedValue::bytes(k).retag(f.tag.clone()),
|
||||||
|
None => UntaggedValue::nothing().retag(f.tag.clone()),
|
||||||
|
};
|
||||||
|
r.insert("physical".to_string(), b);
|
||||||
Value {
|
Value {
|
||||||
value: UntaggedValue::row(r),
|
value: UntaggedValue::row(r),
|
||||||
tag: f.tag,
|
tag: f.tag,
|
||||||
|
|
Loading…
Reference in a new issue