Skip to content

fix(native-chat): preserve large structured command results - #17707

Merged
brennanb2025 merged 4 commits into
mainfrom
brennanb2025/fix-native-chat-large-results
Aug 31, 2026
Merged

brennanb2025 merged 4 commits into
mainfrom
brennanb2025/fix-native-chat-large-results

Conversation

@brennanb2025

@brennanb2025 brennanb2025 commented Aug 31, 2026 •

Copy link
Copy Markdown
Contributor
Files Added Deleted Net
Test 40 $\color{#1a7f37}{\Huge{\mathbf{+}}}$​6920 $\color{#cf222e}{\Huge{\mathbf{−}}}$​912 $\color{#1a7f37}{\Huge{\mathbf{+}}}$​6008
Prod 103 $\color{#1a7f37}{\Huge{\mathbf{+}}}$​7516 $\color{#cf222e}{\Huge{\mathbf{−}}}$​1501 $\color{#1a7f37}{\Huge{\mathbf{+}}}$​6015

Summary

  • Replace the destructive 1 MiB stdout cutoff with incremental, byte-bounded NDJSON framing and backpressure.
  • Persist large command results through bounded content-addressed journal blobs while keeping memory, disk, replay, and rendering projections bounded.
  • Preserve authoritative tool/turn settlement and make unexpected provider exits visible and recoverable without redispatching messages whose delivery is unknown.
  • Add regression coverage for large valid frames, malformed/unbounded input, quota saturation, recovery, and continued next-turn dispatch.

Validation

  • pnpm tc:node
  • pnpm run check:code-quality:changed — 0 findings across 139 changed files
  • git diff --check
  • Focused suites: 128 tests and 445 tests passed
  • Independent broad verifier: 753 tests and 1,479 tests passed
  • Electron proof: a 1,100,000-character command completed and the same chat accepted a follow-up message

Evidence: docs/native-chat-large-result-electron-evidence.md

@greptile-apps

greptile-apps Bot commented Aug 31, 2026 •

Copy link
Copy Markdown

Too many files changed for review (143 files, 100 file limit).

Bypass the limit by tagging @greptile-apps to review.

@pullfrog pullfrog Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

ℹ️ No critical issues — one scaling note plus a scope question, both non-blocking.

Reviewed changes

Reviewed 142 files across three commits that replace the 1 MiB stdout string-accumulator cutoff with an incremental shared NDJSON framer, persist large command results as content-addressed journal blobs behind a byte/operation-accounted backpressure sink, reserve per-turn lifecycle capacity up front, and turn a proven provider exit into a generation-fenced host recovery event.

  • Bounded non-fatal framing: createIncrementalNdjsonFramer (16 MiB envelope) replaces the quadratic string accumulator; oversized/malformed records are classified from a bounded prefix and settle their pending request without killing a healthy provider.
  • Content-addressed result persistence: item/completed now writes the complete payload as a journal blob with a 16 KiB inline head; the delta coalescer bounds retained streamed text with an explicit truncation marker.
  • Accounted sink backpressure: every queued closure is charged bytes/operations before enqueue, stdout pauses/resumes at watermarks, and a write failure converges on one bounded failed state.
  • Reservation admission: per-dispatch/per-turn/per-item byte + append-slot tokens (rebuilt on reopen) prove a bounded terminal settlement even at quota saturation, including lifecycle-batch rows with idempotent settlement ids.
  • Fenced exit recovery: unexpected-exit vs requested-close, acquisition-generation tokens, observed-exit lease release, and resume-capable-holder-gated reacquisition without redispatching unknown messages.

ℹ️ Out-of-scope root .npmrc deletion changes dependency hoisting

Commit 41c7a85 deletes the root .npmrc (shamefully-hoist=true, minimum-release-age=4320) in a PR otherwise dedicated to the native-chat result fix. shamefully-hoist=true changes where pnpm hoists packages — Electron apps commonly rely on it for native/unbundled module resolution at node_modules root — so removing it can alter build/runtime dependency layout on other machines or CI beyond what the summarized validation (tc:node, focused suites, a local Electron proof) covers. If this cleanup is intentional, confirm it's exercised by packaging CI; if not, it belongs in its own PR so a hoisting regression is bisectable.

Technical details
# Scope question: `.npmrc` deletion bundled with the fix

## Affected sites
- `.npmrc` (deleted) — `shamefully-hoist=true`, `minimum-release-age=4320`

## Required outcome
- Confirm dropping `shamefully-hoist` has no effect on Electron/desktop dependency resolution (packaging/runtime), or split the removal into a separate PR with its own validation.

## Open questions for the human
- Is `shamefully-hoist=true` actually stale under pnpm 10, or does the desktop build still rely on hoisted native modules?

Pullfrog  | Fix all ➔ | Fix 👍s ➔ | View workflow run | Using DeepSeek Pro (free via Pullfrog for OSS) | 𝕏

// so the peak check includes those bytes.
let physicalBytes = Math.max(
this.deps.physicalBytes(),
await journalDirectoryBytes(this.deps.journalDir)

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Every append re-runs journalDirectoryBytes, a full recursive readdir + lstat over the journal directory including every retained blob. Now that this PR makes many large result blobs the normal case, each row write becomes O(total files) — paid again on every geometric streamed checkpoint. Consider maintaining the count incrementally from putJournalBlob/removeJournalBlob and only rescanning on open or when a concurrent opener is actually suspected, reserving the full directory walk for that once-per-open path.

@pullfrog pullfrog Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

ℹ️ No new issues in this increment — one prior non-blocking observation remains open.

Reviewed changes

Reviewed the single new commit 624d5e3 since the prior pullfrog review — a narrow bugfix plus its regression test.

  • Rebuilt append-slot enforcement: JournalLifecycleCapacity.rebuild now passes maxAppendSlots into the tentative-turn reservation, closing a gap where a reopened unresolved submission could over-reserve an append slot past the session's reconstructed limit.
  • Regression coverage: a new test in journal-lifecycle-capacity.test.ts proves rebuild returns false and retains the first slot when two submission reservations need more append slots than are available. The assertion is exact (toBe(false) on the failure path plus toBe(1) on reservedAppendSlots), so it fails against the pre-fix code instead of merely passing alongside it.

No action requested on this commit. The earlier per-append journalDirectoryBytes traversal note and the bundled .npmrc hoisting question are unaffected and remain open for the author.

Pullfrog  | Fix it ➔ | View workflow run | Using DeepSeek Pro (free via Pullfrog for OSS) | 𝕏

@brennanb2025

Copy link
Copy Markdown
Contributor Author

Review status: land after fixes, with one review fix pushed.

  • Same-model review loop completed, including readiness/performance checklist at start and end. It found and fixed a real restart-path quota bug: JournalLifecycleCapacity.rebuild() now applies maxAppendSlots when rebuilding tentative-turn reservations (commit 624d5e3f1d), with regression coverage.
  • Verification passed: focused native-chat/journal suite (140 tests), pnpm tc:node, and changed-code quality (0 findings).
  • OSS precedent review found the bounded incremental framing/backpressure shape consistent with established terminal/agent implementations; no scope-expanding changes were made.
  • Orchestrated Grok Electron validation attached to the exact worktree and verified app identity on CDP 9340. The native Codex chat exercise was blocked because the isolated profile had no Codex credentials; no credentials were copied and no screenshot claiming the changed flow was attached.
  • Current CI failures are unrelated/pre-existing: static analysis flags the unchanged WorktreeJumpPalette.recent-tabs.test.tsx line-count limit, and the Windows package job hit a cmd.exe ETIMEDOUT in the unrelated Cursor hook test. Native smoke, typecheck, package, cross-version wire, and all test shards reported passing.

No mobile-facing surface was touched; SSH/remote behavior is out of scope for this host-local change.

@brennanb2025

Copy link
Copy Markdown
Contributor Author

Electron verification completed on the exact PR worktree using the rendered Orca UI and the load-balanced Codex backend.

Automated verification remains green for the native-chat/journal suite (140 tests), pnpm tc:node, and changed-file code quality checks. The branch is clean and synchronized at commit 624d5e3f1d.

@brennanb2025
brennanb2025 merged commit 5fe3772 into main Aug 31, 2026
29 of 32 checks passed
brennanb2025 added a commit that referenced this pull request Aug 31, 2026
* fix(native-chat): preserve large structured command results (#17707)

* fix(native-chat): preserve large structured command results

* chore: place native chat validation artifacts under docs

* chore: drop stale root package config

* fix(native-chat): enforce rebuilt lifecycle append slots

---------

Co-authored-by: Merge Sim <sim@local>

* chore: omit native-chat reland planning docs

* fix(native-chat): remove journal store import cycle

* fix(native-chat): keep journal factory acyclic

---------

Co-authored-by: Merge Sim <sim@local>
enrick-dev pushed a commit to enrick-dev/orca that referenced this pull request Oct 15, 2026
…#17707)

* fix(native-chat): preserve large structured command results

* chore: place native chat validation artifacts under docs

* chore: drop stale root package config

* fix(native-chat): enforce rebuilt lifecycle append slots

---------

Co-authored-by: Merge Sim <sim@local>
enrick-dev pushed a commit to enrick-dev/orca that referenced this pull request Oct 15, 2026
enrick-dev pushed a commit to enrick-dev/orca that referenced this pull request Oct 15, 2026
…7720)

* fix(native-chat): preserve large structured command results (stablyai#17707)

* fix(native-chat): preserve large structured command results

* chore: place native chat validation artifacts under docs

* chore: drop stale root package config

* fix(native-chat): enforce rebuilt lifecycle append slots

---------

Co-authored-by: Merge Sim <sim@local>

* chore: omit native-chat reland planning docs

* fix(native-chat): remove journal store import cycle

* fix(native-chat): keep journal factory acyclic

---------

Co-authored-by: Merge Sim <sim@local>
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