Skip to content

docs(harness): correct the claim that openhuman cannot resume a parked call (#561) - #777

Merged
M3gA-Mind merged 1 commit into
tinyhumansai:mainfrom
M3gA-Mind:docs/561-correct-resume-claim
Aug 12, 2026
Merged

docs(harness): correct the claim that openhuman cannot resume a parked call (#561)#777
M3gA-Mind merged 1 commit into
tinyhumansai:mainfrom
M3gA-Mind:docs/561-correct-resume-claim

Conversation

@M3gA-Mind

@M3gA-Mind M3gA-Mind commented Aug 12, 2026

Copy link
Copy Markdown
Collaborator

Summary

Comment only. No behaviour change.

src/harness/policy.rs asserted that openhuman "genuinely cannot be resumed
here". That is false as a blanket statement, and the assertion is why nobody
checked
— it reads as a settled fact while being an untested inference. Four
PRs (#612, #625, #633, #672) worked around the symptom without anyone verifying
the premise.

openhuman never claimed impossibility. Its own ToolPolicyDecision::RequireApproval
doc says session execution currently treats the variant as fail-closed, and
that "callers that can prompt for approval may branch on this variant and retry
after approval is granted". It also already ships durable approval
interrupt-and-resume — for delegation, on tinyagents' graph executor.

The comment now records the two things that are actually true, because only one
of them is a wall:

  • Resolving inline is incidental. The block happens in a single wrap_tool
    middleware. That hook is async and may call next.run zero or more times —
    tinyagents pins exactly that with wrap_tool_retries_next_until_success.
    Awaiting a verdict there and then dispatching is representable today with no
    upstream change.
  • Durably suspending is structural. The agent turn runs on AgentHarness,
    which has no checkpointer; AgentRun is not Serialize; and the turn is a
    live async task holding the model context, bounded by the run's wall-clock
    deadline.

And the sentence that decides the design, which is the one this correction
exists to put in front of the next reader: an in-memory await survives neither
a long approval nor a process restart, so against this crate's seven-day
standing-grant ceiling it is a leak rather than a mechanism.
Re-issuing stays
correct here until the turn is checkpointable.

This PR deliberately does not implement suspend/resume and does not
recommend a shape. There are two candidate designs — a checkpointer on the agent
engine, versus a bounded in-memory await for short approvals — and that is a
human's decision, not one to take on the back of a comment fix.

Full analysis is on #561, including the detail that most
changes how that issue should be scoped: even the graph executor's resume
re-runs its interrupted node rather than continuing a suspended call. So
re-dispatch and the durable design are the same kind of mechanism at
different grain — the cost can be narrowed, but "approving costs a re-dispatch"
probably cannot be driven to zero.

Closes nothing. #561 stays open for the design decision; this only removes the
false premise that was standing in front of it.

API Or Behavior Changes

None. Documentation comment only — no code, no signatures, no tests changed.

Tests

  • cargo fmt --all -- --check — exit 0
  • cargo check --locked --all-features --all-targets — exit 0
  • cargo clippy --locked --no-deps --features openhuman,tinycortex --all-targets -- -D warnings — exit 0
  • cargo test --features openhuman,tinycortex — exit 0, 3388 passed, 0 failed, 3 ignored

No revert-and-check, stated deliberately rather than omitted. This adds no
test and changes no behaviour, so there is nothing whose removal could turn a
test red; performing one would be exactly the vacuous green this repo's
process warns about. What was checked instead: the added text introduces no
[...] intra-doc links (verified against the added lines in isolation), so
rustdoc has no new reference to resolve and cannot break on it.

  • cargo fmt --all -- --check
  • cargo clippy --all-targets -- -D warnings (run as the gated lane: --locked --no-deps --features openhuman,tinycortex --all-targets)
  • cargo build --all-targets (N/A as spelled — covered by cargo check --locked --all-features --all-targets, the stricter lane, which builds every target under every feature)
  • cargo test (run as cargo test --features openhuman,tinycortex)

Documentation

This change is the documentation. Nothing under docs/ states the
resume/re-dispatch rationale — it lives in this module header, which is where a
reader of the approval path arrives — so nothing there went stale.

Summary by CodeRabbit

  • Documentation
    • Clarified approval behavior in the harness, including that approval calls are re-issued rather than resumed.
    • Documented the distinction between inline approval handling and durable suspension across long waits or restarts.

…d call (tinyhumansai#561)

Comment only; no behaviour change.

This module asserted openhuman "genuinely cannot be resumed here". That is
false as a blanket statement, and the assertion is why nobody checked: it reads
as a settled fact while being an untested inference. openhuman never claimed
impossibility — its own `ToolPolicyDecision::RequireApproval` doc says session
execution *currently* treats the variant as fail-closed and that callers able to
prompt for approval "may branch on this variant and retry". It also already
ships durable approval interrupt-and-resume for delegation, on tinyagents'
graph executor.

Two separate things are true, and only one of them is a wall:

  Resolving inline is INCIDENTAL. The block happens in one `wrap_tool`
  middleware; that hook is async and may call `next.run` zero or more times,
  which tinyagents pins with `wrap_tool_retries_next_until_success`. Awaiting a
  verdict there and then dispatching needs no upstream change.

  Durably suspending is STRUCTURAL. The agent turn runs on `AgentHarness`,
  which has no checkpointer; `AgentRun` is not `Serialize`; and the turn is a
  live async task holding the model context, bounded by the run's wall-clock
  deadline.

Which is what settles the design, and is the sentence worth keeping: an
in-memory await survives neither a long approval nor a process restart, so
against this crate's seven-day standing-grant ceiling it is a leak rather than
a mechanism. Re-issuing stays correct here until the turn is checkpointable.

Full analysis on tinyhumansai#561, including why even the graph executor's `resume` re-runs
its interrupted node rather than continuing a suspended call — so re-dispatch
and the durable design are the same kind of mechanism at different grain.
@M3gA-Mind

Copy link
Copy Markdown
Collaborator Author

@coderabbitai review

@oxoxDev oxoxDev left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

This is the most valuable kind of correction, and the sentence that earns it is the diagnosis rather than the fix:

the assertion is why nobody checked — it reads as a settled fact while being an untested inference

Four PRs worked around a symptom because a comment asserted a wall that was never verified. Going to openhuman's own doc — which says session execution currently treats the variant as fail-closed, and that callers able to prompt "may branch on this variant and retry after approval is granted" — is the check nobody did.

Splitting the claim into the two things that are actually true is what makes the correction useful rather than merely accurate: resolving inline is incidental (one async wrap_tool middleware that may call next.run zero or more times, pinned upstream by wrap_tool_retries_next_until_success, so await-then-dispatch is representable today with no upstream change), while durably suspending is structural (no checkpointer on AgentHarness, AgentRun is not Serialize). Only the second is a wall, and conflating them is what turned a design constraint into a design assumption.

0 major. 1 follow-through, and it is the point. Approving.

The corrected claim lives in five files; this PR fixes one

src/company/types.rs
src/harness/brain.rs
src/harness/policy.rs      ← corrected here
src/policy/consequence.rs
src/policy/judgement.rs

After this lands, four files still assert the thing this PR establishes is false — and the one being corrected is the only one without a behaviour decision resting on it. The two that matter most are untouched:

  • consequence.rs, on parks_under_auto: Reach::Money does not park, because "openhuman resolves a RequireApproval inline and never re-dispatches, so a parked search is a search that never happens and an agent with no search invents citations".
  • judgement.rs (#338's arm): web_search is kept out of the group-only stop on the identical reasoning, and that reasoning is why the Reach pairing exists at all.

Both are live decisions about what does not park, justified by the premise being retracted. I am not arguing either conclusion is wrong — an inline await still blocks the turn, so "the operator is asked and the call then proceeds" may land in the same place as today for those tools. But the reason written at both sites is now known to be shakier than it reads, and this repo has spent the day being bitten by exactly that: a justification that stops describing the code, on an exclusion nobody re-derives.

Correcting one copy and leaving four is worse than the status quo in one specific way — a reader who finds judgement.rs has no signal that policy.rs now contradicts it. Either carry the correction to all five, or leave a pointer at the two behaviour-bearing ones saying the premise is qualified and where.

Worth an issue for the substantive question too, separately from the comments: if await-then-dispatch is representable today, is the Reach::Money carve-out still the right shape, or was it a workaround for a wall that is not there? That is a real design question this PR has just unlocked, and it should not live only in a corrected comment.

Before merging: 13 commits behind, one file, comment-only. Nothing else outstanding.

@coderabbitai

coderabbitai Bot commented Aug 12, 2026

Copy link
Copy Markdown
⚠️ Action not completed

Already reviewed.

Note: CodeRabbit is an incremental review system and does not re-review already reviewed commits. This command is applicable only when automatic reviews are paused.

@coderabbitai

coderabbitai Bot commented Aug 12, 2026

Copy link
Copy Markdown

Review Change Stack

Important

Review skipped

No new commits to review since the last review.

⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro Plus

Run ID: 8b454aa0-f2b6-4492-8e8e-9d085626d0d7

You can disable this status message by setting the reviews.review_status to false in the CodeRabbit configuration file.

Use the checkbox below for a quick retry:

  • 🔍 Trigger review

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro Plus

Run ID: 0fee2442-0b9f-4fc8-b872-478d4dd38435

📥 Commits

Reviewing files that changed from the base of the PR and between bc44f51 and 1832898.

📒 Files selected for processing (1)
  • src/harness/policy.rs

📝 Walkthrough

Walkthrough

The harness policy documentation now distinguishes inline approval handling from durable suspension. It explains that durable suspension requires checkpointable state, which the harness does not provide, so approved calls are re-issued.

Changes

Approval resumption documentation

Layer / File(s) Summary
Clarify approval handling constraints
src/harness/policy.rs
The documentation now explains that inline approval is possible, but durable suspension is unavailable without checkpointing, serialization, and restart-surviving task state. Approved calls are re-issued.

Estimated code review effort: 1 (Trivial) | ~2 minutes

Suggested reviewers: oxoxdev, senamakel

Poem

I’m a rabbit with a policy pen,
Clarifying calls that run again.
Inline approval hops in sight,
Durable state needs more than night.
Re-issued calls now read just right.

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title clearly identifies the documentation correction about resuming parked calls, which is the main change in the pull request.

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@tinysweeper tinysweeper 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.

tinysweeper found nothing blocking. Approving.

             $0.0056 · 9,576 in / 949 out · 6,312 cached (66%) · z-ai/glm-5.2
critique:    $0.0019 · 2,175 in / 509 out · 1,612 cached (74%) · z-ai/glm-5.2
security:    $0.0014 · 2,154 in / 115 out · 768 cached (36%)   · z-ai/glm-5.2
tests:       $0.0010 · 2,069 in / 160 out · 1,549 cached (75%) · z-ai/glm-5.2
description: $0.0013 · 3,178 in / 165 out · 2,383 cached (75%) · z-ai/glm-5.2

@tinysweeper

tinysweeper Bot commented Aug 12, 2026

Copy link
Copy Markdown

What this change touches

1 file, +28 -3 across 1 component. It reaches 6 untouched components (60 graph nodes walked). 1 further component left out to keep the diagram readable.

flowchart LR
  n0["src/harness<br/>1 file +28 -3"]:::changed
  n1["src/harness<br/>8 files reached"]:::impacted
  n2["src/ports<br/>3 files reached"]:::impacted
  n3["src/runtime<br/>2 files reached"]:::impacted
  n4["src/company<br/>1 file reached"]:::impacted
  n5["src/metering<br/>1 file reached"]:::impacted
  n6["src/policy<br/>1 file reached"]:::impacted
  n1 -->|19 refs| n2
  n1 -->|14 refs| n3
  n1 -->|12 refs| n4
  n3 -->|4 refs| n2
  n1 -->|2 refs| n6
  n3 -->|2 refs| n1
  n1 -->|1 ref| n5
  n2 -->|1 ref| n4
  n5 -->|1 ref| n2
  n5 -->|1 ref| n4
  classDef changed fill:#0d4429,stroke:#238636,color:#e6edf3
  classDef impacted fill:#161b22,stroke:#6e7681,color:#c9d1d9
  classDef flagged fill:#5a1e02,stroke:#d93f0b,color:#ffffff
  classDef blocking fill:#67060c,stroke:#f85149,color:#ffffff
Loading

Green: changed. Grey: untouched, reached through an import or a call. Orange: has findings. Red: has a finding that blocks the merge.

Component Files Lines Findings
src/harness changed 1 +28 -3
src/harness reached 8
src/ports reached 3
src/runtime reached 2
src/company reached 1
src/metering reached 1
src/policy reached 1
Changed files

src/harness

  • src/harness/policy.rs

tinysweeper 0.1.0

@tinysweeper tinysweeper Bot added the priority: p3 Whenever. Cosmetic, a nicety, or a cleanup with no user visible effect. label Aug 12, 2026
@M3gA-Mind
M3gA-Mind merged commit 9557d3b into tinyhumansai:main Aug 12, 2026
14 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

priority: p3 Whenever. Cosmetic, a nicety, or a cleanup with no user visible effect.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants