mirror of
https://github.com/nushell/nushell.git
synced 2025-06-30 14:40:06 +02:00
Filesize formatting (#456)
* configure the format of filesize * type-o * removed some comments * updated tests * accomodated filesize_metric better, added test
This commit is contained in:
@ -17,6 +17,8 @@ im = "15.0.0"
|
||||
serde_json = { version = "1.0", optional = true }
|
||||
nu-json = { path = "../nu-json" }
|
||||
typetag = "0.1.8"
|
||||
num-format = "0.4.0"
|
||||
sys-locale = "0.1.0"
|
||||
|
||||
[features]
|
||||
plugin = ["serde_json"]
|
||||
|
@ -14,6 +14,7 @@ pub struct Config {
|
||||
pub footer_mode: FooterMode,
|
||||
pub animate_prompt: bool,
|
||||
pub float_precision: i64,
|
||||
pub filesize_format: String,
|
||||
pub without_color: bool,
|
||||
}
|
||||
|
||||
@ -28,6 +29,7 @@ impl Default for Config {
|
||||
footer_mode: FooterMode::Never,
|
||||
animate_prompt: ANIMATE_PROMPT_DEFAULT,
|
||||
float_precision: 4,
|
||||
filesize_format: "auto".into(),
|
||||
without_color: false,
|
||||
}
|
||||
}
|
||||
@ -74,7 +76,7 @@ impl Value {
|
||||
config.use_grid_icons = value.as_bool()?;
|
||||
}
|
||||
"footer_mode" => {
|
||||
let val_str = value.as_string()?;
|
||||
let val_str = value.as_string()?.to_lowercase();
|
||||
config.footer_mode = match val_str.as_ref() {
|
||||
"auto" => FooterMode::Auto,
|
||||
"never" => FooterMode::Never,
|
||||
@ -94,6 +96,9 @@ impl Value {
|
||||
"without_color" => {
|
||||
config.without_color = value.as_bool()?;
|
||||
}
|
||||
"filesize_format" => {
|
||||
config.filesize_format = value.as_string()?.to_lowercase();
|
||||
}
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
|
@ -5,13 +5,16 @@ mod range;
|
||||
mod stream;
|
||||
mod unit;
|
||||
|
||||
use byte_unit::ByteUnit;
|
||||
use chrono::{DateTime, FixedOffset};
|
||||
use chrono_humanize::HumanTime;
|
||||
pub use from_value::FromValue;
|
||||
use indexmap::map::IndexMap;
|
||||
use num_format::{Locale, ToFormattedString};
|
||||
pub use range::*;
|
||||
use serde::{Deserialize, Serialize};
|
||||
pub use stream::*;
|
||||
use sys_locale::get_locale;
|
||||
pub use unit::*;
|
||||
|
||||
use std::collections::HashMap;
|
||||
@ -1474,16 +1477,114 @@ pub fn format_duration(duration: i64) -> String {
|
||||
}
|
||||
|
||||
fn format_filesize(num_bytes: i64, config: &Config) -> String {
|
||||
// Allow the user to specify how they want their numbers formatted
|
||||
let filesize_format_var = get_config_filesize_format(config);
|
||||
|
||||
let byte = byte_unit::Byte::from_bytes(num_bytes as u128);
|
||||
let adj_byte =
|
||||
if filesize_format_var.0 == byte_unit::ByteUnit::B && filesize_format_var.1 == "auto" {
|
||||
byte.get_appropriate_unit(!config.filesize_metric)
|
||||
} else {
|
||||
byte.get_adjusted_unit(filesize_format_var.0)
|
||||
};
|
||||
|
||||
if byte.get_bytes() == 0u128 {
|
||||
return "—".to_string();
|
||||
}
|
||||
match adj_byte.get_unit() {
|
||||
byte_unit::ByteUnit::B => {
|
||||
let locale_string = get_locale().unwrap_or_else(|| String::from("en-US"));
|
||||
// Since get_locale() and Locale::from_name() don't always return the same items
|
||||
// we need to try and parse it to match. For instance, a valid locale is de_DE
|
||||
// however Locale::from_name() wants only de so we split and parse it out.
|
||||
let locale_string = locale_string.replace("_", "-"); // en_AU -> en-AU
|
||||
let locale = match Locale::from_name(&locale_string) {
|
||||
Ok(loc) => loc,
|
||||
_ => {
|
||||
let all = num_format::Locale::available_names();
|
||||
let locale_prefix = &locale_string.split('-').collect::<Vec<&str>>();
|
||||
if all.contains(&locale_prefix[0]) {
|
||||
// eprintln!("Found alternate: {}", &locale_prefix[0]);
|
||||
Locale::from_name(locale_prefix[0]).unwrap_or(Locale::en)
|
||||
} else {
|
||||
// eprintln!("Unable to find matching locale. Defaulting to en-US");
|
||||
Locale::en
|
||||
}
|
||||
}
|
||||
};
|
||||
let locale_byte = adj_byte.get_value() as u64;
|
||||
let locale_byte_string = locale_byte.to_formatted_string(&locale);
|
||||
|
||||
let byte = byte.get_appropriate_unit(config.filesize_metric);
|
||||
|
||||
match byte.get_unit() {
|
||||
byte_unit::ByteUnit::B => format!("{} B ", byte.get_value()),
|
||||
_ => byte.format(1),
|
||||
if filesize_format_var.1 == "auto" {
|
||||
format!("{} B", locale_byte_string)
|
||||
} else {
|
||||
locale_byte_string
|
||||
}
|
||||
}
|
||||
_ => adj_byte.format(1),
|
||||
}
|
||||
}
|
||||
|
||||
fn get_config_filesize_format(config: &Config) -> (ByteUnit, &str) {
|
||||
// We need to take into account config.filesize_metric so, if someone asks for KB
|
||||
// filesize_metric is true, return KiB
|
||||
let filesize_format = match config.filesize_format.as_str() {
|
||||
"b" => (byte_unit::ByteUnit::B, ""),
|
||||
"kb" => {
|
||||
if config.filesize_metric {
|
||||
(byte_unit::ByteUnit::KiB, "")
|
||||
} else {
|
||||
(byte_unit::ByteUnit::KB, "")
|
||||
}
|
||||
}
|
||||
"kib" => (byte_unit::ByteUnit::KiB, ""),
|
||||
"mb" => {
|
||||
if config.filesize_metric {
|
||||
(byte_unit::ByteUnit::MiB, "")
|
||||
} else {
|
||||
(byte_unit::ByteUnit::MB, "")
|
||||
}
|
||||
}
|
||||
"mib" => (byte_unit::ByteUnit::MiB, ""),
|
||||
"gb" => {
|
||||
if config.filesize_metric {
|
||||
(byte_unit::ByteUnit::GiB, "")
|
||||
} else {
|
||||
(byte_unit::ByteUnit::GB, "")
|
||||
}
|
||||
}
|
||||
"gib" => (byte_unit::ByteUnit::GiB, ""),
|
||||
"tb" => {
|
||||
if config.filesize_metric {
|
||||
(byte_unit::ByteUnit::TiB, "")
|
||||
} else {
|
||||
(byte_unit::ByteUnit::TB, "")
|
||||
}
|
||||
}
|
||||
"tib" => (byte_unit::ByteUnit::TiB, ""),
|
||||
"pb" => {
|
||||
if config.filesize_metric {
|
||||
(byte_unit::ByteUnit::PiB, "")
|
||||
} else {
|
||||
(byte_unit::ByteUnit::PB, "")
|
||||
}
|
||||
}
|
||||
"pib" => (byte_unit::ByteUnit::PiB, ""),
|
||||
"eb" => {
|
||||
if config.filesize_metric {
|
||||
(byte_unit::ByteUnit::EiB, "")
|
||||
} else {
|
||||
(byte_unit::ByteUnit::EB, "")
|
||||
}
|
||||
}
|
||||
"eib" => (byte_unit::ByteUnit::EiB, ""),
|
||||
"zb" => {
|
||||
if config.filesize_metric {
|
||||
(byte_unit::ByteUnit::ZiB, "")
|
||||
} else {
|
||||
(byte_unit::ByteUnit::ZB, "")
|
||||
}
|
||||
}
|
||||
"zib" => (byte_unit::ByteUnit::ZiB, ""),
|
||||
_ => (byte_unit::ByteUnit::B, "auto"),
|
||||
};
|
||||
|
||||
filesize_format
|
||||
}
|
||||
|
Reference in New Issue
Block a user