Detect ChatGPT's chat wall on the composer surface, roll over before Send, and rotate long convergences #67
No reviewers
Labels
No labels
accessibility
bug
documentation
duplicate
enhancement
good first issue
help wanted
invalid
question
wontfix
No milestone
No project
No assignees
1 participant
Notifications
Due date
No due date set.
Dependencies
No dependencies set
Reference
x/ego-chat!67
Loading…
Reference in a new issue
No description provided.
Delete branch "feat/exhaustion-and-rotation"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Summary
Stacked on #66. ChatGPT shows its conversation-length wall and usage limits on the composer surface, not in the reply, so Ego Chat could not see them. This PR reads that surface, stops before Send when a chat is already full, rolls a convergence over on a wall seen before Send, and rotates long convergences before they reach the wall.
Background, from ChatGPT's own client code (read-only, 2026-09-23): the 2026 wall sentence, "You've reached the maximum length for this conversation, but you can keep talking by starting a new chat.", is server-provided and arrives through the composer banner system. "Continue in a new chat" belongs to ChatGPT's silent context truncation, which starts far below the wall, so it is only advisory.
Composer-surface observer (
src/composer-surface.mjs).div#thread-bottom. It skips the editor, the disclaimer, message content and hidden nodes, and has no page-wide fallback.continuationOffered: "Continue in a new chat" with a usable composer.Before Send. Two reads one second apart that agree stop the exchange before the policy menu and before anything is composed. The stop codes are
chatgpt_conversation_exhausted_before_send,chatgpt_conversation_closed_before_sendandchatgpt_quota_limited_before_send. They are human-only and exported inPRE_SEND_PROVEN_STOP_CODES. The first read is kept on the Send record.After Send. Capture attributes a composer state to the turn only when all of these hold:
The result is
providerTerminalwith sourcecomposer_surface, including a new kindconversation_closedthat maps tochatgpt_conversation_closed. Banner labels also feed the pending capture'sstatusLabelsand the Jev terminal judgment.Rollover on a pre-Send wall (
src/conversation-continuation.mjs). A checkpoint variant without a confirmed Send hands the review, which was never delivered, to the successor unchanged. A closed chat or a usage limit pauses the convergence and never rolls over. Manual continuation is unchanged.Size and proactive rotation.
egoChatExchangesandegoChatBytesinside the existing head-commit write, with no extra revision.conversationSizewithrotationRecommended, set at 120 or more messages or after a continuation offer.rotation.maxMessages: 120 by default, 40 to 1000, or"off". They never rotate under manual continuation.ego-chat-main, the long-lived main chat, defaults to rotation"off", and itsrotationRecommendedstays false. An explicitrotationinput still applies there. The MCP schema leaves an omittedrotationto the broker, because only the broker knows this per-binding default.An MCP instruction explains the
_before_sendcodes. For a usage limit it says to wait for the reset and retry on the same binding.Browser contract 30, runtime generation 2026-09-23.7.
Verification
npm test: 1188 tests, 1187 pass, 1 skipped.cargo test: 33 + 1.#thread-bottom.Not yet done
Not merged, released or installed.
The wall's real DOM has never been observed. These can only be confirmed live:
A wall that renders differently falls through to the previous behaviour, a normal pending capture.
Known gap: a convergence paused on a closed chat or a usage limit has no resume path. The only way out is to cancel it.