fix(#2639): cancel_loose_end kind="todo" clears without a bash round-trip
Adds a real MCP-side path for the workaround #2639 documented: dial the in-container HIVE_AGENT_SOCKET directly from cancel_loose_end (kind:"todo") instead of shelling out via a tracked bash task (nc -U ...), which is what was spawning a fresh completion todo on every clear and cascading forever. hive-agent-mcp/src/mcp/render.rs: renamed local_todos's socket-dial guts into a shared dial_agent_socket(req) helper, added mark_local_todo_done(id) on top of it (MarkTodoDone request already existed server-side, unused until now). mod.rs wires kind:"todo" into cancel_loose_end ahead of the question/reminder/approval parse. args.rs + render.rs + docs/tools/bash.md text updated to point at the new path instead of the old raw nc invocation.
This commit is contained in:
parent
4989bcdb5e
commit
c4deca99db
4 changed files with 70 additions and 20 deletions
|
|
@ -35,8 +35,8 @@ pub use args::{
|
|||
pub use render::{annotate_retries, format_ack, format_agent_meta, format_recv};
|
||||
|
||||
use render::{
|
||||
format_matrix_summary, local_todos, loose_end_kind_label, matrix_unread_summary,
|
||||
parse_loose_end_kind, render_loose_ends, reply_err,
|
||||
format_matrix_summary, local_todos, loose_end_kind_label, mark_local_todo_done,
|
||||
matrix_unread_summary, parse_loose_end_kind, render_loose_ends, reply_err,
|
||||
};
|
||||
|
||||
/// Write (or remove) the status file in the agent's own `state/` directory.
|
||||
|
|
@ -413,12 +413,34 @@ impl AgentServer {
|
|||
cancel rows where you're the asker / owner. Returns `ok` or an error string.\n\
|
||||
`kind` may also be `\"approval\"` to withdraw a pending approval you submitted \
|
||||
(before the operator acts on it) — root agent (`ruth`) only; the server rejects \
|
||||
`approval` kind for all other callers."
|
||||
`approval` kind for all other callers.\n\
|
||||
`kind` may also be `\"todo\"` to clear one of your own loose-ends-v2 todos \
|
||||
(bash-task completions, matrix unread, forge activity — the id in the \
|
||||
`get_loose_ends` `todo #N` line) — this dials the in-container socket directly, \
|
||||
no bash task involved, so it's safe to call repeatedly without spawning more \
|
||||
todos."
|
||||
)]
|
||||
async fn cancel_loose_end(&self, Parameters(args): Parameters<CancelLooseEndArgs>) -> String {
|
||||
let log = format!("{args:?}");
|
||||
let id = args.id;
|
||||
run_tool_envelope("cancel_loose_end", log, async move {
|
||||
if args.kind.trim().eq_ignore_ascii_case("todo") {
|
||||
return match mark_local_todo_done(id).await {
|
||||
Some(hive_agent_sock::Response::Acked { count }) if count > 0 => {
|
||||
format!("cleared todo {id}")
|
||||
}
|
||||
Some(hive_agent_sock::Response::Acked { .. }) => {
|
||||
format!("no such todo {id} (already cleared, or never existed)")
|
||||
}
|
||||
Some(hive_agent_sock::Response::Err { message }) => {
|
||||
format!("cancel_loose_end failed: {message}")
|
||||
}
|
||||
Some(other) => format!("cancel_loose_end unexpected response: {other:?}"),
|
||||
None => "cancel_loose_end: local todo socket unavailable \
|
||||
(HIVE_AGENT_SOCKET unset or harness unreachable)"
|
||||
.to_owned(),
|
||||
};
|
||||
}
|
||||
let kind = match parse_loose_end_kind(&args.kind) {
|
||||
Ok(k) => k,
|
||||
Err(e) => return e,
|
||||
|
|
|
|||
Loading…
Reference in a new issue