use super::{Verb, find, table};
pub fn roster() -> String {
let rows: Vec<(String, &str)> = table()
.iter()
.map(|verb| (verb.usage(), verb.summary))
.collect();
let widest = rows.iter().map(|(usage, _)| usage.len()).max().unwrap_or(0);
rows.iter()
.map(|(usage, summary)| format!(" {usage:widest$} {summary}"))
.collect::<Vec<String>>()
.join("\n")
}
pub fn page(word: &str) -> Result<String, String> {
let Some(verb) = find(word) else {
return Err(format!(
"no verb named {word:?} — `lernie help` lists every one"
));
};
Ok(rendered(&verb))
}
fn rendered(verb: &Verb) -> String {
format!(
"usage: {}\n\n{}\n\n{}",
verb.usage(),
verb.summary,
wrapped(verb.detail)
)
}
fn wrapped(text: &str) -> String {
const WIDTH: usize = 72;
let mut lines: Vec<String> = Vec::new();
for word in text.split_whitespace() {
match lines.last_mut() {
Some(line) if line.len() + 1 + word.len() <= WIDTH => {
line.push(' ');
line.push_str(word);
}
_ => lines.push(word.to_owned()),
}
}
lines.join("\n")
}
#[cfg(test)]
mod tests;