use std::io::Write;
use std::path::PathBuf;
use anyhow::Context;
use crate::listing::render_table;
use crate::reserve::{self, HeldClaim};
const ACQUIRED_CAVEAT: &str = "note: `acquired` is best-effort client-declared metadata (the holder's commit \
date), not a server-attested clock.";
#[derive(Debug, clap::Subcommand)]
pub(crate) enum ReservationCommand {
List(ListArgs),
}
#[derive(Debug, clap::Args)]
pub(crate) struct ListArgs {
#[arg(short = 'k', long)]
kind: Option<String>,
#[arg(short = 'r', long)]
remote: Option<String>,
#[arg(short = 'p', long)]
path: Option<PathBuf>,
}
pub(crate) fn dispatch(cmd: ReservationCommand) -> anyhow::Result<()> {
match cmd {
ReservationCommand::List(args) => run_list(args),
}
}
fn run_list(args: ListArgs) -> anyhow::Result<()> {
let root = crate::root::find(args.path, &crate::root::default_markers())?;
let remote = match args.remote {
Some(r) => r,
None => crate::git::resolve_remote(&root)?.context(
"no reservation remote configured (pass --remote, or configure a git remote)",
)?,
};
let kind = args.kind.map(|k| k.trim().to_ascii_uppercase());
let held = reserve::survey(&root, &remote, kind.as_deref())?;
print_survey(&held);
Ok(())
}
fn print_survey(held: &[HeldClaim]) {
let mut out = std::io::stdout();
if held.is_empty() {
_ = writeln!(out, "no held reservations");
return;
}
let mut grid: Vec<Vec<String>> = vec![row("canonical", "holder", "acquired")];
let mut held: Vec<&HeldClaim> = held.iter().collect();
held.sort_by(|a, b| a.canonical.cmp(&b.canonical));
for h in held {
grid.push(vec![
h.canonical.clone(),
h.holder.clone(),
h.acquired.clone(),
]);
}
_ = write!(
out,
"{}",
render_table(&grid, crate::tty::stdout_terminal_width())
);
_ = writeln!(out, "{ACQUIRED_CAVEAT}");
}
fn row(a: &str, b: &str, c: &str) -> Vec<String> {
vec![a.to_owned(), b.to_owned(), c.to_owned()]
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn acquired_caveat_states_client_declared_best_effort() {
assert!(ACQUIRED_CAVEAT.contains("best-effort"));
assert!(ACQUIRED_CAVEAT.contains("client-declared"));
assert!(ACQUIRED_CAVEAT.contains("not a server-attested clock"));
}
}