Skip to content

fix(hermes): Hermes v0.20 one-shot compat — cli_close + auxiliary task rows - #4

Merged
askclaw-vesper merged 4 commits into
mainfrom
fix/hermes-v020-compat
Aug 20, 2026
Merged

askclaw-vesper merged 4 commits into
mainfrom
fix/hermes-v020-compat

Conversation

@askclaw-vesper

Copy link
Copy Markdown
Collaborator

Summary

Two fail-closed rejections hit when running the hermes-cli adapter against Hermes Agent v0.20.4 — both false negatives on clean, successful one-shot turns:

  1. cli_close end_reason rejected. Hermes v0.20+ finalizes one-shot (-q/-Q) sessions via _flush_one_shot_session_store, writing ended_at/end_reason='cli_close' on normal CLI exit. The adapter only accepted 'completed', so every clean turn failed with ended with reason 'cli_close', not a clean completion. cli_close carries the same meaning for the one-shot contract and stays gated by ended_at window consistency plus the process-exit terminal basis.

  2. Auxiliary model calls polluted identity. Hermes records auxiliary calls (title generation, vision, compression, …) in session_model_usage alongside the main turn, with a non-empty task column and often a different model/provider. The adapter counted every usage row, so a clean turn failed with observed model set [...] is not exactly one model. Now only task ''/NULL rows (main conversation) prove identity; pre-task schemas keep the old all-rows behavior.

Evidence

Both bugs were reproduced live during a real three-Hermes-profile dialogue (madp run --launch against three distinct HERMES_HOMEs), then fixed and re-run to completion with validate --require-git --require-runner-completion returning ok: true.

Tests

  • New test_ended_with_cli_close_reason_is_accepted in the terminal-field matrix.
  • New HermesUsageTaskFilterTests — the entire accept/reject matrix re-runs against a task-column schema, plus: auxiliary rows ignored, NULL task counts as main, two main-task models still rejected.
  • Full suite: 227 passed, 22 subtests; scripts/verify.py → {"ok": true}.

Notes

  • No protocol semantics change: dirty end_reasons (error, canceled, …) and multi-model main conversations still fail closed.
  • Found during a MADP self-improvement dialogue; the accompanying design proposals are filed as a separate issue.

Hermes v0.20+ finalizes one-shot (-q/-Q) sessions via
_flush_one_shot_session_store, which writes ended_at/end_reason
'cli_close' on normal CLI exit. The adapter only accepted 'completed',
so every clean one-shot turn on current Hermes failed closed with
'not a clean completion'. cli_close carries the same meaning for the
one-shot contract and stays gated by ended_at window consistency plus
the process-exit terminal basis.
Hermes records auxiliary model calls (title generation, vision,
compression, ...) in session_model_usage alongside the main turn, with
a non-empty task column and often a different model/provider. The
adapter counted every usage row, so a clean one-shot turn failed
closed with 'observed model set is not exactly one model' whenever an
auxiliary call ran (Hermes v0.20 does this routinely).

Only task ''/NULL rows (main conversation) now prove model/provider
identity; schemas without a task column keep the old all-rows
behavior. Matrix tests rerun against both schema variants.

@adaptcom adaptcom Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Confidence Score: 4/5

Summary

Accepts Hermes v0.20 cli_close as a clean one-shot end_reason and derives model identity from main-task usage rows only. Fail-closed paths preserved, new matrix coverage is thorough, full suite green; low merge risk.

Important Files Changed

File Overview
src/multi_agent_dialogue/adapters/hermes.py Adds cli_close to clean end reasons; filters usage rows to main-task only
tests/test_real_contracts.py cli_close acceptance test plus task-filter subclass rerunning full terminal matrix

Findings

  • tests/test_real_contracts.py:656 matrix docstring still lists only NULL/''/'completed' as clean end_reasons; update it to include cli_close.

↻ Re-run review · View in Adapt

Comment thread src/multi_agent_dialogue/adapters/hermes.py
Comment thread src/multi_agent_dialogue/adapters/hermes.py
askclaw-vesper and others added 2 commits August 20, 2026 04:58
…pi_call_count

Review follow-up: match the session_model_usage task column
case-insensitively (SQLite identifier semantics) so an oddly-cased
"Task" schema still triggers the main-conversation filter, and state
explicitly in the proof docs that api_call_count covers
main-conversation calls only on task-column schemas. Also documents
cli_close in the technical reference.
@askclaw-vesper
askclaw-vesper merged commit 6a8a861 into main Aug 20, 2026
2 checks passed
@askclaw-vesper
askclaw-vesper deleted the fix/hermes-v020-compat branch August 20, 2026 05:09
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant