diff options
author | Alex Auvolat <alex@adnab.me> | 2023-06-13 17:02:42 +0200 |
---|---|---|
committer | Alex Auvolat <alex@adnab.me> | 2023-06-13 17:14:11 +0200 |
commit | 90b2d43eb49d49c3aef4f501a30cf2f181adb183 (patch) | |
tree | f7f7c15547e2f2072a1841fcb2350c272faf3c9d /src/format-table | |
parent | bf19a44fd93584d5250a2e98e5b1d3a2de6d59d1 (diff) | |
parent | 01346143ca09eab262f0d8f8a0a744c2f6d667cc (diff) | |
download | garage-90b2d43eb49d49c3aef4f501a30cf2f181adb183.tar.gz garage-90b2d43eb49d49c3aef4f501a30cf2f181adb183.zip |
Merge branch 'main' into next
Diffstat (limited to 'src/format-table')
-rw-r--r-- | src/format-table/Cargo.toml | 12 | ||||
-rw-r--r-- | src/format-table/README.md | 13 | ||||
-rw-r--r-- | src/format-table/lib.rs | 49 |
3 files changed, 74 insertions, 0 deletions
diff --git a/src/format-table/Cargo.toml b/src/format-table/Cargo.toml new file mode 100644 index 00000000..9e31e211 --- /dev/null +++ b/src/format-table/Cargo.toml @@ -0,0 +1,12 @@ +[package] +name = "format_table" +version = "0.1.1" +authors = ["Alex Auvolat <alex@adnab.me>"] +edition = "2018" +license = "AGPL-3.0" +description = "Format tables with a stupid API" +repository = "https://git.deuxfleurs.fr/Deuxfleurs/garage" +readme = "README.md" + +[lib] +path = "lib.rs" diff --git a/src/format-table/README.md b/src/format-table/README.md new file mode 100644 index 00000000..d918bdf4 --- /dev/null +++ b/src/format-table/README.md @@ -0,0 +1,13 @@ +# `format_table` + +Format tables with a stupid API. [Documentation](https://docs.rs/format_table). + +Example: + +```rust +let mut table = vec!["product\tquantity\tprice".to_string()]; +for (p, q, r) in [("tomato", 12, 15), ("potato", 10, 20), ("rice", 5, 12)] { + table.push(format!("{}\t{}\t{}", p, q, r)); +} +format_table::format_table(table); +``` diff --git a/src/format-table/lib.rs b/src/format-table/lib.rs new file mode 100644 index 00000000..55252ba9 --- /dev/null +++ b/src/format-table/lib.rs @@ -0,0 +1,49 @@ +//! Format tables with a stupid API. +//! +//! Example: +//! +//! ```rust +//! let mut table = vec!["product\tquantity\tprice".to_string()]; +//! for (p, q, r) in [("tomato", 12, 15), ("potato", 10, 20), ("rice", 5, 12)] { +//! table.push(format!("{}\t{}\t{}", p, q, r)); +//! } +//! format_table::format_table(table); +//! ``` +//! +//! A table to be formatted is a `Vec<String>`, containing one string per line. +//! Table columns in each line are separated by a `\t` character. + +/// Format a table and return the result as a string. +pub fn format_table_to_string(data: Vec<String>) -> String { + let data = data + .iter() + .map(|s| s.split('\t').collect::<Vec<_>>()) + .collect::<Vec<_>>(); + + let columns = data.iter().map(|row| row.len()).fold(0, std::cmp::max); + let mut column_size = vec![0; columns]; + + let mut out = String::new(); + + for row in data.iter() { + for (i, col) in row.iter().enumerate() { + column_size[i] = std::cmp::max(column_size[i], col.chars().count()); + } + } + + for row in data.iter() { + for (col, col_len) in row[..row.len() - 1].iter().zip(column_size.iter()) { + out.push_str(col); + (0..col_len - col.chars().count() + 2).for_each(|_| out.push(' ')); + } + out.push_str(row[row.len() - 1]); + out.push('\n'); + } + + out +} + +/// Format a table and print the result to stdout. +pub fn format_table(data: Vec<String>) { + print!("{}", format_table_to_string(data)); +} |