Repository navigation
feat(cli): loading indicators for indexes list and usage - #215
Conversation
Both commands sat silent while fetching. `indexes list` gets one spinner over the whole fetch - the unscoped path is a whole-workspace scan (connections enumeration + managed-DB discovery + per-table index reads) that can take seconds. The database discovery inside the scan (databases::list_database_ids) drops its nested "Loading databases..." wakeup spinner so two indicatif bars never fight over the same line; `databases list` itself keeps the wakeup-hint spinner. `usage` gets a plain spinner around its single request.
| // whole-workspace scan (many requests) that otherwise sits silent. | ||
| // The database discovery inside is deliberately spinner-less | ||
| // (databases::list_database_ids) so nothing fights for the line. | ||
| let spinner = crate::util::spinner("Loading indexes…"); |
There was a problem hiding this comment.
This spinner is only cleared at line 525, after the match block — so it is never cleared on the error path. Every fetch inside the match (list_one_table, collect_connection_wide, and list_database_ids) exits via e.exit() on API error, which calls ApiError::print() (writes directly to stderr with eprintln!) and then process::exit(1). When that happens, the steady-ticking spinner is still active: the error message gets written over/interleaved with the spinner line, and the spinner is left stuck on the terminal after exit.
This is exactly the "two bars fight over the same line" problem you deliberately avoided — and in usage.rs you handled the equivalent case correctly by capturing the Result and clearing the spinner before e.exit():
let result = api.get_json("/usage", &query);
spinner.finish_and_clear();
let u: Usage = result.unwrap_or_else(|e| e.exit());The indexes path needs the same treatment, but the exits happen deep inside the helper functions, so finish_and_clear() after the match doesn't cover them. Consider having the fetch helpers return Result so the caller can clear the spinner before exiting, or otherwise ensure the spinner is finished before any error is printed.
There was a problem hiding this comment.
Review — Blocking
Blocking Issues
src/commands/indexes.rs:507— the "Loading indexes…" spinner is only cleared after the match block (line 525), so it is never cleared on the error path. All three fetch helpers exit viae.exit()on API error, which prints to stderr andprocess::exit(1)s while the steady-ticking spinner is still active. This interleaves the error message with the spinner and leaves the spinner stuck on the terminal — the same line-fight you correctly avoided inusage.rs.
Action Required
Ensure the spinner is finished before any error is printed on the indexes path. Since the exits happen inside the fetch helpers, cleaning up after the match is not sufficient — have the helpers return Result so the caller can finish_and_clear() before e.exit() (mirroring the usage.rs pattern).
Codecov Report❌ Patch coverage is
📢 Thoughts on this report? Let us know! |
* feat(databases): show created_at in list and show commands Adds a CREATED column to `databases list` and a created_at row to `databases show`. Uses the updated SDK models from sdk-rust feat/database-timestamps (PR #909 in runtimedb). Cargo.toml temporarily points to local sdk-rust path; update to published version once sdk-rust feat/database-timestamps is released. * chore: update hotdata SDK to v0.8.1 (created_at on databases) --------- Co-authored-by: Eddie A Tejeda <669988+eddietejeda@users.noreply.github.com>
'hotdata ingest datasources' now browses the catalog of available datasource types; 'connectors' stays as a hidden alias. Help, error hints, README, and the skill follow. Co-authored-by: Eddie A Tejeda <669988+eddietejeda@users.noreply.github.com>
The fetch helpers called e.exit() (process::exit) internally, leaving the indicatif spinner live on the terminal when any API call failed. Convert list_one_table, list_one_table_scan, collect_tables, connection_lookup, managed_db_connection_ids, workspace_scan_targets, and collect_connection_wide to return Result<_, ApiError>, then finish_and_clear() the spinner in list() before unwrap_or_else(|e| e.exit()) -- matching the usage.rs pattern.
Both commands sat silent while fetching:
indexes list: one spinner over the whole fetch — the unscoped path is a whole-workspace scan (connections enumeration + managed-DB discovery + per-table index reads) that can take seconds. The database discovery inside the scan (databases::list_database_ids) becomes deliberately spinner-less so its nested "Loading databases…" bar never fights the outer one for the line;databases listitself keeps the wakeup-hint spinner.usage: plain spinner around its single request, cleared before rendering or error exit.Smoke-tested both against prod.