refactor, fix filters, add column renaming, general fixes
This commit is contained in:
parent
d12637ce75
commit
d8ce9df7bc
5 changed files with 368 additions and 135 deletions
|
@ -10,7 +10,7 @@ pub fn get_args() -> ArgMatches {
|
|||
.arg(
|
||||
arg!(-c --column <COLUMN>... "Specify output columns")
|
||||
.required(false)
|
||||
.default_value("path"),
|
||||
.default_value("file.title:Title"),
|
||||
)
|
||||
.get_matches()
|
||||
}
|
||||
|
|
43
src/lib.rs
43
src/lib.rs
|
@ -66,7 +66,15 @@ fn get_key(d: &Document, key: &str) -> String {
|
|||
}
|
||||
if let Some(val) = d.frontmatter.as_mapping().unwrap().get(key) {
|
||||
// TODO : Fix format
|
||||
format!("{val:?}")
|
||||
match val {
|
||||
serde_yaml::Value::Null => String::new(),
|
||||
serde_yaml::Value::Bool(b) => b.to_string(),
|
||||
serde_yaml::Value::Number(n) => n.to_string(),
|
||||
serde_yaml::Value::String(s) => s.to_owned(),
|
||||
serde_yaml::Value::Sequence(_v) => todo!(),
|
||||
serde_yaml::Value::Mapping(_o) => todo!(),
|
||||
serde_yaml::Value::Tagged(_) => unimplemented!(),
|
||||
}
|
||||
} else {
|
||||
String::new()
|
||||
}
|
||||
|
@ -76,7 +84,7 @@ type Table = Vec<Vec<String>>;
|
|||
|
||||
/// Build a table with specified columns from index
|
||||
#[must_use]
|
||||
pub fn select_columns(i: &Index, col: &[&String]) -> Table {
|
||||
pub fn select_columns(i: &Index, col: &[String]) -> Table {
|
||||
let mut rows = vec![];
|
||||
|
||||
for doc in &i.documents {
|
||||
|
@ -93,21 +101,40 @@ pub fn select_columns(i: &Index, col: &[&String]) -> Table {
|
|||
/// Apply filters to the documents of the index returning a new filtered index
|
||||
#[must_use]
|
||||
pub fn filter_documents(i: Index, filters: &[txd::filter::Filter]) -> Index {
|
||||
// TODO : Implement option for chaining filters with AND OR
|
||||
let docs: Vec<_> = i
|
||||
.documents
|
||||
.into_iter()
|
||||
.filter_map(|x| {
|
||||
for f in filters {
|
||||
let a = get_key(&x, &f.0);
|
||||
let mut is_included = true;
|
||||
|
||||
let a = txd::parse(&a);
|
||||
for f in filters {
|
||||
let a_str = get_key(&x, &f.0);
|
||||
let mut a = txd::parse(&a_str);
|
||||
let b = txd::parse(&f.2);
|
||||
|
||||
if a.compare(f.1, b) {
|
||||
return Some(x);
|
||||
log::debug!("Trying to compare {a:?} and {b:?} with {:?}", f.1);
|
||||
|
||||
if a_str.is_empty() {
|
||||
// TODO : Maybe add explicit null instead of empty string
|
||||
is_included = false;
|
||||
break;
|
||||
}
|
||||
|
||||
if !a.same_as(&b) {
|
||||
log::debug!("trying to cast a to string because of different types");
|
||||
a = txd::DataType::String(a_str);
|
||||
}
|
||||
|
||||
if !a.compare(f.1, b) {
|
||||
is_included = false
|
||||
}
|
||||
}
|
||||
None
|
||||
if is_included {
|
||||
Some(x)
|
||||
} else {
|
||||
None
|
||||
}
|
||||
})
|
||||
.collect();
|
||||
|
||||
|
|
66
src/main.rs
66
src/main.rs
|
@ -1,11 +1,16 @@
|
|||
use std::io::IsTerminal;
|
||||
|
||||
use mdq::{filter_documents, scan_dir, select_columns};
|
||||
use prettytable::{Cell, Row};
|
||||
|
||||
mod args;
|
||||
|
||||
// TODO : Add debug logging
|
||||
// TODO : Add documentation comments
|
||||
// TODO : Add tests
|
||||
|
||||
fn main() {
|
||||
env_logger::init();
|
||||
let args = args::get_args();
|
||||
//println!("{args:?}");
|
||||
|
||||
let root_dir = args.get_one::<String>("dir").unwrap();
|
||||
|
||||
|
@ -17,11 +22,24 @@ fn main() {
|
|||
None
|
||||
};
|
||||
|
||||
let columns: Vec<_> = if let Some(columns) = args.get_many::<String>("column") {
|
||||
columns.collect()
|
||||
} else {
|
||||
vec![]
|
||||
};
|
||||
let columns: Vec<_> = args
|
||||
.get_many::<String>("column")
|
||||
.unwrap()
|
||||
.cloned()
|
||||
.collect();
|
||||
log::info!("selected columns: {columns:?}");
|
||||
|
||||
let columns: Vec<(_, _)> = columns
|
||||
.into_iter()
|
||||
.map(|x| {
|
||||
let (column, header_rename) = x.split_once(':').unwrap_or((&x, &x));
|
||||
|
||||
(column.to_owned(), header_rename.to_owned())
|
||||
})
|
||||
.collect();
|
||||
|
||||
let (columns, headers): (Vec<_>, Vec<_>) = columns.into_iter().unzip();
|
||||
|
||||
let filters: Vec<_> = if let Some(filters) = args.get_many::<String>("filter") {
|
||||
filters.collect()
|
||||
} else {
|
||||
|
@ -48,30 +66,34 @@ fn main() {
|
|||
};
|
||||
|
||||
if output_json {
|
||||
let data = serde_json::json!(
|
||||
let mut data = serde_json::json!(
|
||||
{
|
||||
"columns": columns,
|
||||
"results": data
|
||||
}
|
||||
);
|
||||
if columns != headers {
|
||||
data.as_object_mut()
|
||||
.unwrap()
|
||||
.insert("headers".into(), headers.into());
|
||||
}
|
||||
println!("{}", serde_json::to_string(&data).unwrap());
|
||||
return;
|
||||
}
|
||||
|
||||
let mut table = prettytable::Table::new();
|
||||
|
||||
let headers = columns
|
||||
.iter()
|
||||
.map(|cell| Cell::new(cell))
|
||||
.collect::<Vec<Cell>>();
|
||||
table.set_titles(Row::new(headers));
|
||||
|
||||
// Add rows to the table
|
||||
for row in data {
|
||||
let cells: Vec<Cell> = row.iter().map(|cell| Cell::new(cell)).collect();
|
||||
table.add_row(Row::new(cells));
|
||||
if data.is_empty() {
|
||||
return;
|
||||
}
|
||||
|
||||
// Print the table to the console
|
||||
table.printstd();
|
||||
let mut table = comfy_table::Table::new();
|
||||
|
||||
table.set_header(headers);
|
||||
table.load_preset(comfy_table::presets::UTF8_FULL_CONDENSED);
|
||||
if !std::io::stdout().is_terminal() {
|
||||
// TODO : Output as CSV?
|
||||
table.load_preset(comfy_table::presets::NOTHING);
|
||||
}
|
||||
table.add_rows(data);
|
||||
|
||||
println!("{table}");
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue