feat: local-mode WS terminal failure — pause after N reconnects, typed error (#22) - #33

Merged
AndresL230 merged 12 commits into
mainfrom
feat/22-ws-terminal-failure
May 14, 2026
Merged

feat: local-mode WS terminal failure — pause after N reconnects, typed error (#22)#33
AndresL230 merged 12 commits into
mainfrom
feat/22-ws-terminal-failure

Conversation

@AndresL230

Copy link
Copy Markdown
Contributor

Summary

  • Adds RecostLocalUnreachableError to the public API; sibling to the RecostAuthError hierarchy added in PR feat: 401 auth-failure handling — suspend after N, typed errors (#16) #32.
  • Pauses the local WebSocket transport after maxConsecutiveReconnectFailures (default 20) consecutive failed reconnects. Recovery is restart-only.
  • One-time stderr warning at the threshold, regardless of debug flag.
  • Existing onError(err: Error) signature is unchanged — hosts narrow via instanceof.

Closes#22.

Wave 1 of the issue-waves roadmap (docs/superpowers/roadmap-2026-05-13-issue-waves.md); Sub-plan B for cross-SDK parity is tracked at recost-dev/middleware-python#32.

Branch contents

12 commits — 2 leading docs commits (roadmap + spec, then plan) ride at the head of the implementation branch by intent (combined PR rather than separate docs/impl PRs):

  • 856dce9 docs(roadmap): 6-wave issue plan + Wave 1 Sub-plan A spec
  • 1938601 docs(plan): WS terminal failure implementation plan
  • 3 setup feat commits (types, public-api export, ResolvedConfig wiring)
  • 1 bundled feat impl commit (TDD test + production code together)
  • 5 test commits (threshold trip, send-after-pause, counter reset, configurable threshold, cloud-mode-unaffected + idempotency)
  • 1 README docs commit

Test plan

  • npm run test — 235/235 green (228 baseline + 7 new cases)
  • npm run lint — clean
  • npm run build — clean dual ESM + CJS + DTS
  • Manually verify in a host process with no VS Code extension running: SDK stops spinning after the threshold, one stderr line is printed, one onError(RecostLocalUnreachableError) fires, CPU drops to zero.

- roadmap-2026-05-13-issue-waves.md: groups the 11 open issues into
six 2-issue waves with theme, files, ordering rationale, and
status placeholders. Tracking doc for the orchestrator.
- specs/2026-05-13-ws-terminal-failure-design.md: design for #22
(WebSocket reconnect terminal failure mode). Mirrors the #16
pattern shipped in PR #32: typed RecostLocalUnreachableError
through onError, threshold counter (default 20, reuses existing
_reconnectAttempts), one-shot stderr line, send() becomes
silent no-op once paused, restart-only recovery.
…#22)
12-task plan for Wave 1 Sub-plan A. Mirrors PR #32's structure:
3 setup tasks (types, exports, ResolvedConfig wiring), 1 TDD-red
task, 1 implementation+green task with bundled commit, 5 test
tasks (threshold trip, send-after-pause no-op, counter reset on
successful connect, configurable threshold, cloud-mode-unaffected
+ idempotency), 1 README docs task, 1 final verification + PR
task. Each test is calibrated to keep wall-clock under vitest's
default per-test timeout.
Roadmap also updated to reference middleware-python#32 (Sub-plan
B follow-up issue, filed separately).
@coderabbitai

Copy link
Copy Markdown

Warning

Rate limit exceeded

@AndresL230 has exceeded the limit for the number of commits that can be reviewed per hour. Please wait 17 minutes and 5 seconds before requesting another review.

You’ve run out of usage credits. Purchase more in the billing tab.

⌛ How to resolve this issue?

After the wait time has elapsed, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

We recommend that you space out your commits to avoid hitting the rate limit.

🚦 How do rate limits work?

CodeRabbit enforces hourly rate limits for each developer per organization.

Our paid plans have higher rate limits than the trial, open-source and free plans. In all cases, we re-allow further reviews after a brief timeout.

Please see our FAQ for further information.

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: 8744f10a-1a87-4263-b20e-b9fc0ea91cf9

📥 Commits

Reviewing files that changed from the base of the PR and between 3f28421 and d69cf4e.

📒 Files selected for processing (8)
  • README.md
  • docs/superpowers/plans/2026-05-13-ws-terminal-failure.md
  • docs/superpowers/roadmap-2026-05-13-issue-waves.md
  • docs/superpowers/specs/2026-05-13-ws-terminal-failure-design.md
  • src/core/transport.ts
  • src/core/types.ts
  • src/index.ts
  • tests/transport.test.ts
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feat/22-ws-terminal-failure

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 and usage tips.

@AndresL230
AndresL230 merged commit c38595e into mainMay 14, 2026
1 check passed
@AndresL230
AndresL230 deleted the feat/22-ws-terminal-failure branch May 21, 2026 04:15
Sign up for freeto 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.

WebSocket reconnect retries forever, no terminal failure mode

1 participant

@AndresL230
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Add copy buttons to all
 blocks\n(function() {\n function addCopyButtons() {\n document.querySelectorAll('pre code').forEach(function(codeBlock) {\n if (codeBlock.parentElement.hasAttribute('data-copy-added')) return;\n codeBlock.parentElement.setAttribute('data-copy-added', 'true');\n \n var btn = document.createElement('button');\n btn.textContent = 'Copy';\n btn.style.cssText = 'position:absolute;top:4px;right:4px;padding:2px 8px;font-size:11px;background:#4ecdc4;border:none;border-radius:4px;color:#1a1a2e;cursor:pointer;opacity:0.7;transition:opacity 0.2s;';\n btn.onmouseover = function() { this.style.opacity = '1'; };\n btn.onmouseout = function() { this.style.opacity = '0.7'; };\n btn.onclick = function() {\n navigator.clipboard.writeText(codeBlock.textContent).then(function() {\n btn.textContent = 'Copied!';\n setTimeout(function() { btn.textContent = 'Copy'; }, 1500);\n });\n };\n codeBlock.parentElement.style.position = 'relative';\n codeBlock.parentElement.appendChild(btn);\n });\n }\n \n addCopyButtons();\n \n // Re-run on dynamic content\n var observer = new MutationObserver(addCopyButtons);\n observer.observe(document.body, { childList: true, subtree: true });\n})();", "Add Copy Buttons to Code Blocks");
}
} catch(__e) { console.warn('[Userscript:Add Copy Buttons to Code Blocks]', __e); }
})();
(function(){
try {
var __m = "github.com";
var __re = new RegExp('^' + "github\\.com" + '
Skip to content

feat: local-mode WS terminal failure — pause after N reconnects, typed error (#22) - #33

Merged
AndresL230 merged 12 commits into
mainfrom
feat/22-ws-terminal-failure
May 14, 2026
Merged

feat: local-mode WS terminal failure — pause after N reconnects, typed error (#22)#33
AndresL230 merged 12 commits into
mainfrom
feat/22-ws-terminal-failure

Conversation

@AndresL230

Copy link
Copy Markdown
Contributor

Summary

  • Adds RecostLocalUnreachableError to the public API; sibling to the RecostAuthError hierarchy added in PR feat: 401 auth-failure handling — suspend after N, typed errors (#16) #32.
  • Pauses the local WebSocket transport after maxConsecutiveReconnectFailures (default 20) consecutive failed reconnects. Recovery is restart-only.
  • One-time stderr warning at the threshold, regardless of debug flag.
  • Existing onError(err: Error) signature is unchanged — hosts narrow via instanceof.

Closes#22.

Wave 1 of the issue-waves roadmap (docs/superpowers/roadmap-2026-05-13-issue-waves.md); Sub-plan B for cross-SDK parity is tracked at recost-dev/middleware-python#32.

Branch contents

12 commits — 2 leading docs commits (roadmap + spec, then plan) ride at the head of the implementation branch by intent (combined PR rather than separate docs/impl PRs):

  • 856dce9 docs(roadmap): 6-wave issue plan + Wave 1 Sub-plan A spec
  • 1938601 docs(plan): WS terminal failure implementation plan
  • 3 setup feat commits (types, public-api export, ResolvedConfig wiring)
  • 1 bundled feat impl commit (TDD test + production code together)
  • 5 test commits (threshold trip, send-after-pause, counter reset, configurable threshold, cloud-mode-unaffected + idempotency)
  • 1 README docs commit

Test plan

  • npm run test — 235/235 green (228 baseline + 7 new cases)
  • npm run lint — clean
  • npm run build — clean dual ESM + CJS + DTS
  • Manually verify in a host process with no VS Code extension running: SDK stops spinning after the threshold, one stderr line is printed, one onError(RecostLocalUnreachableError) fires, CPU drops to zero.

- roadmap-2026-05-13-issue-waves.md: groups the 11 open issues into
six 2-issue waves with theme, files, ordering rationale, and
status placeholders. Tracking doc for the orchestrator.
- specs/2026-05-13-ws-terminal-failure-design.md: design for #22
(WebSocket reconnect terminal failure mode). Mirrors the #16
pattern shipped in PR #32: typed RecostLocalUnreachableError
through onError, threshold counter (default 20, reuses existing
_reconnectAttempts), one-shot stderr line, send() becomes
silent no-op once paused, restart-only recovery.
…#22)
12-task plan for Wave 1 Sub-plan A. Mirrors PR #32's structure:
3 setup tasks (types, exports, ResolvedConfig wiring), 1 TDD-red
task, 1 implementation+green task with bundled commit, 5 test
tasks (threshold trip, send-after-pause no-op, counter reset on
successful connect, configurable threshold, cloud-mode-unaffected
+ idempotency), 1 README docs task, 1 final verification + PR
task. Each test is calibrated to keep wall-clock under vitest's
default per-test timeout.
Roadmap also updated to reference middleware-python#32 (Sub-plan
B follow-up issue, filed separately).
@coderabbitai

Copy link
Copy Markdown

Warning

Rate limit exceeded

@AndresL230 has exceeded the limit for the number of commits that can be reviewed per hour. Please wait 17 minutes and 5 seconds before requesting another review.

You’ve run out of usage credits. Purchase more in the billing tab.

⌛ How to resolve this issue?

After the wait time has elapsed, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

We recommend that you space out your commits to avoid hitting the rate limit.

🚦 How do rate limits work?

CodeRabbit enforces hourly rate limits for each developer per organization.

Our paid plans have higher rate limits than the trial, open-source and free plans. In all cases, we re-allow further reviews after a brief timeout.

Please see our FAQ for further information.

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: 8744f10a-1a87-4263-b20e-b9fc0ea91cf9

📥 Commits

Reviewing files that changed from the base of the PR and between 3f28421 and d69cf4e.

📒 Files selected for processing (8)
  • README.md
  • docs/superpowers/plans/2026-05-13-ws-terminal-failure.md
  • docs/superpowers/roadmap-2026-05-13-issue-waves.md
  • docs/superpowers/specs/2026-05-13-ws-terminal-failure-design.md
  • src/core/transport.ts
  • src/core/types.ts
  • src/index.ts
  • tests/transport.test.ts
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feat/22-ws-terminal-failure

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 and usage tips.

@AndresL230
AndresL230 merged commit c38595e into mainMay 14, 2026
1 check passed
@AndresL230
AndresL230 deleted the feat/22-ws-terminal-failure branch May 21, 2026 04:15
Sign up for freeto 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.

WebSocket reconnect retries forever, no terminal failure mode

1 participant

@AndresL230
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Force GitHub README to respect dark mode\n(function() {\n var style = document.createElement('style');\n style.textContent = '\n .markdown-body {\n color-scheme: dark light;\n }\n .markdown-body pre { background: #161b22 !important; }\n .markdown-body code { background: rgba(110, 118, 129, 0.4) !important; }\n .markdown-body table th, .markdown-body table td { border-color: #30363d !important; }\n .markdown-body img { background: #0d1117; }\n .markdown-body blockquote { border-left-color: #8b949e; }\n .markdown-body hr { border-color: #30363d; }\n ';\n document.head.appendChild(style);\n})();", "GitHub Dark Mode README Fix"); } } catch(__e) { console.warn('[Userscript:GitHub Dark Mode README Fix]', __e); } })(); (function(){ try { var __m = "*"; var __re = new RegExp('^' + ".*" + '
Skip to content

feat: local-mode WS terminal failure — pause after N reconnects, typed error (#22) - #33

Merged
AndresL230 merged 12 commits into
mainfrom
feat/22-ws-terminal-failure
May 14, 2026
Merged

feat: local-mode WS terminal failure — pause after N reconnects, typed error (#22)#33
AndresL230 merged 12 commits into
mainfrom
feat/22-ws-terminal-failure

Conversation

@AndresL230

Copy link
Copy Markdown
Contributor

Summary

  • Adds RecostLocalUnreachableError to the public API; sibling to the RecostAuthError hierarchy added in PR feat: 401 auth-failure handling — suspend after N, typed errors (#16) #32.
  • Pauses the local WebSocket transport after maxConsecutiveReconnectFailures (default 20) consecutive failed reconnects. Recovery is restart-only.
  • One-time stderr warning at the threshold, regardless of debug flag.
  • Existing onError(err: Error) signature is unchanged — hosts narrow via instanceof.

Closes#22.

Wave 1 of the issue-waves roadmap (docs/superpowers/roadmap-2026-05-13-issue-waves.md); Sub-plan B for cross-SDK parity is tracked at recost-dev/middleware-python#32.

Branch contents

12 commits — 2 leading docs commits (roadmap + spec, then plan) ride at the head of the implementation branch by intent (combined PR rather than separate docs/impl PRs):

  • 856dce9 docs(roadmap): 6-wave issue plan + Wave 1 Sub-plan A spec
  • 1938601 docs(plan): WS terminal failure implementation plan
  • 3 setup feat commits (types, public-api export, ResolvedConfig wiring)
  • 1 bundled feat impl commit (TDD test + production code together)
  • 5 test commits (threshold trip, send-after-pause, counter reset, configurable threshold, cloud-mode-unaffected + idempotency)
  • 1 README docs commit

Test plan

  • npm run test — 235/235 green (228 baseline + 7 new cases)
  • npm run lint — clean
  • npm run build — clean dual ESM + CJS + DTS
  • Manually verify in a host process with no VS Code extension running: SDK stops spinning after the threshold, one stderr line is printed, one onError(RecostLocalUnreachableError) fires, CPU drops to zero.

- roadmap-2026-05-13-issue-waves.md: groups the 11 open issues into
six 2-issue waves with theme, files, ordering rationale, and
status placeholders. Tracking doc for the orchestrator.
- specs/2026-05-13-ws-terminal-failure-design.md: design for #22
(WebSocket reconnect terminal failure mode). Mirrors the #16
pattern shipped in PR #32: typed RecostLocalUnreachableError
through onError, threshold counter (default 20, reuses existing
_reconnectAttempts), one-shot stderr line, send() becomes
silent no-op once paused, restart-only recovery.
…#22)
12-task plan for Wave 1 Sub-plan A. Mirrors PR #32's structure:
3 setup tasks (types, exports, ResolvedConfig wiring), 1 TDD-red
task, 1 implementation+green task with bundled commit, 5 test
tasks (threshold trip, send-after-pause no-op, counter reset on
successful connect, configurable threshold, cloud-mode-unaffected
+ idempotency), 1 README docs task, 1 final verification + PR
task. Each test is calibrated to keep wall-clock under vitest's
default per-test timeout.
Roadmap also updated to reference middleware-python#32 (Sub-plan
B follow-up issue, filed separately).
@coderabbitai

Copy link
Copy Markdown

Warning

Rate limit exceeded

@AndresL230 has exceeded the limit for the number of commits that can be reviewed per hour. Please wait 17 minutes and 5 seconds before requesting another review.

You’ve run out of usage credits. Purchase more in the billing tab.

⌛ How to resolve this issue?

After the wait time has elapsed, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

We recommend that you space out your commits to avoid hitting the rate limit.

🚦 How do rate limits work?

CodeRabbit enforces hourly rate limits for each developer per organization.

Our paid plans have higher rate limits than the trial, open-source and free plans. In all cases, we re-allow further reviews after a brief timeout.

Please see our FAQ for further information.

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: 8744f10a-1a87-4263-b20e-b9fc0ea91cf9

📥 Commits

Reviewing files that changed from the base of the PR and between 3f28421 and d69cf4e.

📒 Files selected for processing (8)
  • README.md
  • docs/superpowers/plans/2026-05-13-ws-terminal-failure.md
  • docs/superpowers/roadmap-2026-05-13-issue-waves.md
  • docs/superpowers/specs/2026-05-13-ws-terminal-failure-design.md
  • src/core/transport.ts
  • src/core/types.ts
  • src/index.ts
  • tests/transport.test.ts
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feat/22-ws-terminal-failure

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 and usage tips.

@AndresL230
AndresL230 merged commit c38595e into mainMay 14, 2026
1 check passed
@AndresL230
AndresL230 deleted the feat/22-ws-terminal-failure branch May 21, 2026 04:15
Sign up for freeto 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.

WebSocket reconnect retries forever, no terminal failure mode

1 participant

@AndresL230
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Highlight search terms from Google/DuckDuckGo/Bing referrer\n(function() {\n var ref = document.referrer;\n var terms = [];\n \n if (ref.includes('google.com') || ref.includes('duckduckgo.com') || ref.includes('bing.com')) {\n var url = new URL(ref);\n var q = url.searchParams.get('q') || url.searchParams.get('p');\n if (q) {\n terms = q.split(/\\s+/).filter(function(t) { return t.length > 2; });\n }\n }\n \n if (terms.length === 0) return;\n \n var style = document.createElement('style');\n style.textContent = '.userscript-highlight { background: #fbbf24; color: #1a1a2e; padding: 1px 3px; border-radius: 2px; }';\n document.head.appendChild(style);\n \n function highlight(node) {\n if (node.nodeType === 3) { // text node\n var text = node.textContent;\n var found = false;\n terms.forEach(function(term) {\n var regex = new RegExp('(' + term.replace(/[.*+?^${}()|[\\]\\\\]/g, '\\\\') + ')', 'gi');\n if (regex.test(text)) {\n found = true;\n var frag = document.createDocumentFragment();\n var parts = text.split(regex);\n parts.forEach(function(part, i) {\n if (i % 2 === 0) {\n frag.appendChild(document.createTextNode(part));\n } else {\n var span = document.createElement('span');\n span.className = 'userscript-highlight';\n span.textContent = part;\n frag.appendChild(span);\n }\n });\n node.parentNode.replaceChild(frag, node);\n }\n });\n } else if (node.nodeType === 1 && node.childNodes) { // element\n var skipTags = ['SCRIPT', 'STYLE', 'NOSCRIPT', 'TEXTAREA', 'INPUT', 'SELECT'];\n if (!skipTags.includes(node.tagName)) {\n Array.from(node.childNodes).forEach(highlight);\n }\n }\n }\n \n highlight(document.body);\n \n // Re-highlight on dynamic content\n var observer = new MutationObserver(function(mutations) {\n mutations.forEach(function(m) {\n m.addedNodes.forEach(function(node) {\n if (node.nodeType === 1 || node.nodeType === 3) highlight(node);\n });\n });\n });\n observer.observe(document.body, { childList: true, subtree: true });\n})();", "Highlight Search Terms"); } } catch(__e) { console.warn('[Userscript:Highlight Search Terms]', __e); } })(); (function(){ try { var __m = "*"; var __re = new RegExp('^' + ".*" + '
Skip to content

feat: local-mode WS terminal failure — pause after N reconnects, typed error (#22) - #33

Merged
AndresL230 merged 12 commits into
mainfrom
feat/22-ws-terminal-failure
May 14, 2026
Merged

feat: local-mode WS terminal failure — pause after N reconnects, typed error (#22)#33
AndresL230 merged 12 commits into
mainfrom
feat/22-ws-terminal-failure

Conversation

@AndresL230

Copy link
Copy Markdown
Contributor

Summary

  • Adds RecostLocalUnreachableError to the public API; sibling to the RecostAuthError hierarchy added in PR feat: 401 auth-failure handling — suspend after N, typed errors (#16) #32.
  • Pauses the local WebSocket transport after maxConsecutiveReconnectFailures (default 20) consecutive failed reconnects. Recovery is restart-only.
  • One-time stderr warning at the threshold, regardless of debug flag.
  • Existing onError(err: Error) signature is unchanged — hosts narrow via instanceof.

Closes#22.

Wave 1 of the issue-waves roadmap (docs/superpowers/roadmap-2026-05-13-issue-waves.md); Sub-plan B for cross-SDK parity is tracked at recost-dev/middleware-python#32.

Branch contents

12 commits — 2 leading docs commits (roadmap + spec, then plan) ride at the head of the implementation branch by intent (combined PR rather than separate docs/impl PRs):

  • 856dce9 docs(roadmap): 6-wave issue plan + Wave 1 Sub-plan A spec
  • 1938601 docs(plan): WS terminal failure implementation plan
  • 3 setup feat commits (types, public-api export, ResolvedConfig wiring)
  • 1 bundled feat impl commit (TDD test + production code together)
  • 5 test commits (threshold trip, send-after-pause, counter reset, configurable threshold, cloud-mode-unaffected + idempotency)
  • 1 README docs commit

Test plan

  • npm run test — 235/235 green (228 baseline + 7 new cases)
  • npm run lint — clean
  • npm run build — clean dual ESM + CJS + DTS
  • Manually verify in a host process with no VS Code extension running: SDK stops spinning after the threshold, one stderr line is printed, one onError(RecostLocalUnreachableError) fires, CPU drops to zero.

- roadmap-2026-05-13-issue-waves.md: groups the 11 open issues into
six 2-issue waves with theme, files, ordering rationale, and
status placeholders. Tracking doc for the orchestrator.
- specs/2026-05-13-ws-terminal-failure-design.md: design for #22
(WebSocket reconnect terminal failure mode). Mirrors the #16
pattern shipped in PR #32: typed RecostLocalUnreachableError
through onError, threshold counter (default 20, reuses existing
_reconnectAttempts), one-shot stderr line, send() becomes
silent no-op once paused, restart-only recovery.
…#22)
12-task plan for Wave 1 Sub-plan A. Mirrors PR #32's structure:
3 setup tasks (types, exports, ResolvedConfig wiring), 1 TDD-red
task, 1 implementation+green task with bundled commit, 5 test
tasks (threshold trip, send-after-pause no-op, counter reset on
successful connect, configurable threshold, cloud-mode-unaffected
+ idempotency), 1 README docs task, 1 final verification + PR
task. Each test is calibrated to keep wall-clock under vitest's
default per-test timeout.
Roadmap also updated to reference middleware-python#32 (Sub-plan
B follow-up issue, filed separately).
@coderabbitai

Copy link
Copy Markdown

Warning

Rate limit exceeded

@AndresL230 has exceeded the limit for the number of commits that can be reviewed per hour. Please wait 17 minutes and 5 seconds before requesting another review.

You’ve run out of usage credits. Purchase more in the billing tab.

⌛ How to resolve this issue?

After the wait time has elapsed, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

We recommend that you space out your commits to avoid hitting the rate limit.

🚦 How do rate limits work?

CodeRabbit enforces hourly rate limits for each developer per organization.

Our paid plans have higher rate limits than the trial, open-source and free plans. In all cases, we re-allow further reviews after a brief timeout.

Please see our FAQ for further information.

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: 8744f10a-1a87-4263-b20e-b9fc0ea91cf9

📥 Commits

Reviewing files that changed from the base of the PR and between 3f28421 and d69cf4e.

📒 Files selected for processing (8)
  • README.md
  • docs/superpowers/plans/2026-05-13-ws-terminal-failure.md
  • docs/superpowers/roadmap-2026-05-13-issue-waves.md
  • docs/superpowers/specs/2026-05-13-ws-terminal-failure-design.md
  • src/core/transport.ts
  • src/core/types.ts
  • src/index.ts
  • tests/transport.test.ts
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feat/22-ws-terminal-failure

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 and usage tips.

@AndresL230
AndresL230 merged commit c38595e into mainMay 14, 2026
1 check passed
@AndresL230
AndresL230 deleted the feat/22-ws-terminal-failure branch May 21, 2026 04:15
Sign up for freeto 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.

WebSocket reconnect retries forever, no terminal failure mode

1 participant

@AndresL230
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Strip utm_, fbclid, gclid, etc. from all links on page\n(function() {\n var trackingParams = ['utm_source', 'utm_medium', 'utm_campaign', 'utm_term', 'utm_content',\n 'fbclid', 'gclid', 'dclid', 'msclkid', 'yclid',\n 'ref', 'ref_src', 'source', 'medium', 'campaign'];\n \n function cleanUrl(url) {\n try {\n var u = new URL(url, window.location.origin);\n var changed = false;\n trackingParams.forEach(function(p) {\n if (u.searchParams.has(p)) {\n u.searchParams.delete(p);\n changed = true;\n }\n });\n return changed ? u.toString() : url;\n } catch (e) {\n return url;\n }\n }\n \n function cleanLinks() {\n document.querySelectorAll('a[href]').forEach(function(a) {\n var clean = cleanUrl(a.href);\n if (clean !== a.href) a.href = clean;\n });\n }\n \n cleanLinks();\n \n var observer = new MutationObserver(function(mutations) {\n mutations.forEach(function(m) {\n m.addedNodes.forEach(function(node) {\n if (node.nodeType === 1) {\n if (node.tagName === 'A') cleanLinks();\n node.querySelectorAll('a[href]').forEach(function(a) {\n var clean = cleanUrl(a.href);\n if (clean !== a.href) a.href = clean;\n });\n }\n });\n });\n });\n observer.observe(document.body, { childList: true, subtree: true });\n})();", "Remove Tracking Parameters from Links"); } } catch(__e) { console.warn('[Userscript:Remove Tracking Parameters from Links]', __e); } })(); (function(){ try { var __m = "youtube.com"; var __re = new RegExp('^' + "youtube\\.com" + '
Skip to content

feat: local-mode WS terminal failure — pause after N reconnects, typed error (#22) - #33

Merged
AndresL230 merged 12 commits into
mainfrom
feat/22-ws-terminal-failure
May 14, 2026
Merged

feat: local-mode WS terminal failure — pause after N reconnects, typed error (#22)#33
AndresL230 merged 12 commits into
mainfrom
feat/22-ws-terminal-failure

Conversation

@AndresL230

Copy link
Copy Markdown
Contributor

Summary

  • Adds RecostLocalUnreachableError to the public API; sibling to the RecostAuthError hierarchy added in PR feat: 401 auth-failure handling — suspend after N, typed errors (#16) #32.
  • Pauses the local WebSocket transport after maxConsecutiveReconnectFailures (default 20) consecutive failed reconnects. Recovery is restart-only.
  • One-time stderr warning at the threshold, regardless of debug flag.
  • Existing onError(err: Error) signature is unchanged — hosts narrow via instanceof.

Closes#22.

Wave 1 of the issue-waves roadmap (docs/superpowers/roadmap-2026-05-13-issue-waves.md); Sub-plan B for cross-SDK parity is tracked at recost-dev/middleware-python#32.

Branch contents

12 commits — 2 leading docs commits (roadmap + spec, then plan) ride at the head of the implementation branch by intent (combined PR rather than separate docs/impl PRs):

  • 856dce9 docs(roadmap): 6-wave issue plan + Wave 1 Sub-plan A spec
  • 1938601 docs(plan): WS terminal failure implementation plan
  • 3 setup feat commits (types, public-api export, ResolvedConfig wiring)
  • 1 bundled feat impl commit (TDD test + production code together)
  • 5 test commits (threshold trip, send-after-pause, counter reset, configurable threshold, cloud-mode-unaffected + idempotency)
  • 1 README docs commit

Test plan

  • npm run test — 235/235 green (228 baseline + 7 new cases)
  • npm run lint — clean
  • npm run build — clean dual ESM + CJS + DTS
  • Manually verify in a host process with no VS Code extension running: SDK stops spinning after the threshold, one stderr line is printed, one onError(RecostLocalUnreachableError) fires, CPU drops to zero.

- roadmap-2026-05-13-issue-waves.md: groups the 11 open issues into
six 2-issue waves with theme, files, ordering rationale, and
status placeholders. Tracking doc for the orchestrator.
- specs/2026-05-13-ws-terminal-failure-design.md: design for #22
(WebSocket reconnect terminal failure mode). Mirrors the #16
pattern shipped in PR #32: typed RecostLocalUnreachableError
through onError, threshold counter (default 20, reuses existing
_reconnectAttempts), one-shot stderr line, send() becomes
silent no-op once paused, restart-only recovery.
…#22)
12-task plan for Wave 1 Sub-plan A. Mirrors PR #32's structure:
3 setup tasks (types, exports, ResolvedConfig wiring), 1 TDD-red
task, 1 implementation+green task with bundled commit, 5 test
tasks (threshold trip, send-after-pause no-op, counter reset on
successful connect, configurable threshold, cloud-mode-unaffected
+ idempotency), 1 README docs task, 1 final verification + PR
task. Each test is calibrated to keep wall-clock under vitest's
default per-test timeout.
Roadmap also updated to reference middleware-python#32 (Sub-plan
B follow-up issue, filed separately).
@coderabbitai

Copy link
Copy Markdown

Warning

Rate limit exceeded

@AndresL230 has exceeded the limit for the number of commits that can be reviewed per hour. Please wait 17 minutes and 5 seconds before requesting another review.

You’ve run out of usage credits. Purchase more in the billing tab.

⌛ How to resolve this issue?

After the wait time has elapsed, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

We recommend that you space out your commits to avoid hitting the rate limit.

🚦 How do rate limits work?

CodeRabbit enforces hourly rate limits for each developer per organization.

Our paid plans have higher rate limits than the trial, open-source and free plans. In all cases, we re-allow further reviews after a brief timeout.

Please see our FAQ for further information.

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: 8744f10a-1a87-4263-b20e-b9fc0ea91cf9

📥 Commits

Reviewing files that changed from the base of the PR and between 3f28421 and d69cf4e.

📒 Files selected for processing (8)
  • README.md
  • docs/superpowers/plans/2026-05-13-ws-terminal-failure.md
  • docs/superpowers/roadmap-2026-05-13-issue-waves.md
  • docs/superpowers/specs/2026-05-13-ws-terminal-failure-design.md
  • src/core/transport.ts
  • src/core/types.ts
  • src/index.ts
  • tests/transport.test.ts
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feat/22-ws-terminal-failure

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 and usage tips.

@AndresL230
AndresL230 merged commit c38595e into mainMay 14, 2026
1 check passed
@AndresL230
AndresL230 deleted the feat/22-ws-terminal-failure branch May 21, 2026 04:15
Sign up for freeto 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.

WebSocket reconnect retries forever, no terminal failure mode

1 participant

@AndresL230
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Auto-enable theater mode on YouTube\n(function() {\n function tryTheater() {\n var btn = document.querySelector('button[aria-label=\"Theater mode\"], ytd-player #player button[title=\"Theater mode\"]');\n if (btn && !btn.classList.contains('activated')) {\n btn.click();\n }\n }\n \n // Try immediately\n tryTheater();\n \n // Try after navigation (SPA)\n var lastUrl = location.href;\n setInterval(function() {\n if (location.href !== lastUrl) {\n lastUrl = location.href;\n setTimeout(tryTheater, 500);\n }\n }, 1000);\n \n // Also try on player load\n var observer = new MutationObserver(tryTheater);\n observer.observe(document.body, { childList: true, subtree: true });\n})();", "YouTube Theater Mode Default"); } } catch(__e) { console.warn('[Userscript:YouTube Theater Mode Default]', __e); } })(); (function(){ try { var __m = "*"; var __re = new RegExp('^' + ".*" + '
Skip to content

feat: local-mode WS terminal failure — pause after N reconnects, typed error (#22) - #33

Merged
AndresL230 merged 12 commits into
mainfrom
feat/22-ws-terminal-failure
May 14, 2026
Merged

feat: local-mode WS terminal failure — pause after N reconnects, typed error (#22)#33
AndresL230 merged 12 commits into
mainfrom
feat/22-ws-terminal-failure

Conversation

@AndresL230

Copy link
Copy Markdown
Contributor

Summary

  • Adds RecostLocalUnreachableError to the public API; sibling to the RecostAuthError hierarchy added in PR feat: 401 auth-failure handling — suspend after N, typed errors (#16) #32.
  • Pauses the local WebSocket transport after maxConsecutiveReconnectFailures (default 20) consecutive failed reconnects. Recovery is restart-only.
  • One-time stderr warning at the threshold, regardless of debug flag.
  • Existing onError(err: Error) signature is unchanged — hosts narrow via instanceof.

Closes#22.

Wave 1 of the issue-waves roadmap (docs/superpowers/roadmap-2026-05-13-issue-waves.md); Sub-plan B for cross-SDK parity is tracked at recost-dev/middleware-python#32.

Branch contents

12 commits — 2 leading docs commits (roadmap + spec, then plan) ride at the head of the implementation branch by intent (combined PR rather than separate docs/impl PRs):

  • 856dce9 docs(roadmap): 6-wave issue plan + Wave 1 Sub-plan A spec
  • 1938601 docs(plan): WS terminal failure implementation plan
  • 3 setup feat commits (types, public-api export, ResolvedConfig wiring)
  • 1 bundled feat impl commit (TDD test + production code together)
  • 5 test commits (threshold trip, send-after-pause, counter reset, configurable threshold, cloud-mode-unaffected + idempotency)
  • 1 README docs commit

Test plan

  • npm run test — 235/235 green (228 baseline + 7 new cases)
  • npm run lint — clean
  • npm run build — clean dual ESM + CJS + DTS
  • Manually verify in a host process with no VS Code extension running: SDK stops spinning after the threshold, one stderr line is printed, one onError(RecostLocalUnreachableError) fires, CPU drops to zero.

- roadmap-2026-05-13-issue-waves.md: groups the 11 open issues into
six 2-issue waves with theme, files, ordering rationale, and
status placeholders. Tracking doc for the orchestrator.
- specs/2026-05-13-ws-terminal-failure-design.md: design for #22
(WebSocket reconnect terminal failure mode). Mirrors the #16
pattern shipped in PR #32: typed RecostLocalUnreachableError
through onError, threshold counter (default 20, reuses existing
_reconnectAttempts), one-shot stderr line, send() becomes
silent no-op once paused, restart-only recovery.
…#22)
12-task plan for Wave 1 Sub-plan A. Mirrors PR #32's structure:
3 setup tasks (types, exports, ResolvedConfig wiring), 1 TDD-red
task, 1 implementation+green task with bundled commit, 5 test
tasks (threshold trip, send-after-pause no-op, counter reset on
successful connect, configurable threshold, cloud-mode-unaffected
+ idempotency), 1 README docs task, 1 final verification + PR
task. Each test is calibrated to keep wall-clock under vitest's
default per-test timeout.
Roadmap also updated to reference middleware-python#32 (Sub-plan
B follow-up issue, filed separately).
@coderabbitai

Copy link
Copy Markdown

Warning

Rate limit exceeded

@AndresL230 has exceeded the limit for the number of commits that can be reviewed per hour. Please wait 17 minutes and 5 seconds before requesting another review.

You’ve run out of usage credits. Purchase more in the billing tab.

⌛ How to resolve this issue?

After the wait time has elapsed, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

We recommend that you space out your commits to avoid hitting the rate limit.

🚦 How do rate limits work?

CodeRabbit enforces hourly rate limits for each developer per organization.

Our paid plans have higher rate limits than the trial, open-source and free plans. In all cases, we re-allow further reviews after a brief timeout.

Please see our FAQ for further information.

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: 8744f10a-1a87-4263-b20e-b9fc0ea91cf9

📥 Commits

Reviewing files that changed from the base of the PR and between 3f28421 and d69cf4e.

📒 Files selected for processing (8)
  • README.md
  • docs/superpowers/plans/2026-05-13-ws-terminal-failure.md
  • docs/superpowers/roadmap-2026-05-13-issue-waves.md
  • docs/superpowers/specs/2026-05-13-ws-terminal-failure-design.md
  • src/core/transport.ts
  • src/core/types.ts
  • src/index.ts
  • tests/transport.test.ts
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feat/22-ws-terminal-failure

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 and usage tips.

@AndresL230
AndresL230 merged commit c38595e into mainMay 14, 2026
1 check passed
@AndresL230
AndresL230 deleted the feat/22-ws-terminal-failure branch May 21, 2026 04:15
Sign up for freeto 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.

WebSocket reconnect retries forever, no terminal failure mode

1 participant

@AndresL230
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Remove or un-stick sticky/fixed headers that block content\n(function() {\n function unstick() {\n document.querySelectorAll('header, nav, [role=\"banner\"], .header, .navbar, .sticky, .fixed-top, [style*=\"position: fixed\"], [style*=\"position:sticky\"]').forEach(function(el) {\n if (el.style.position === 'fixed' || el.style.position === 'sticky' || \n getComputedStyle(el).position === 'fixed' || getComputedStyle(el).position === 'sticky') {\n el.style.position = 'static';\n el.style.top = 'auto';\n el.style.zIndex = 'auto';\n }\n });\n }\n \n unstick();\n \n var observer = new MutationObserver(unstick);\n observer.observe(document.body, { childList: true, subtree: true, attributes: true, attributeFilter: ['style', 'class'] });\n})();", "Kill Sticky Headers"); } } catch(__e) { console.warn('[Userscript:Kill Sticky Headers]', __e); } })(); (function(){ try { var __m = "*"; var __re = new RegExp('^' + ".*" + '
Skip to content

feat: local-mode WS terminal failure — pause after N reconnects, typed error (#22) - #33

Merged
AndresL230 merged 12 commits into
mainfrom
feat/22-ws-terminal-failure
May 14, 2026
Merged

feat: local-mode WS terminal failure — pause after N reconnects, typed error (#22)#33
AndresL230 merged 12 commits into
mainfrom
feat/22-ws-terminal-failure

Conversation

@AndresL230

Copy link
Copy Markdown
Contributor

Summary

  • Adds RecostLocalUnreachableError to the public API; sibling to the RecostAuthError hierarchy added in PR feat: 401 auth-failure handling — suspend after N, typed errors (#16) #32.
  • Pauses the local WebSocket transport after maxConsecutiveReconnectFailures (default 20) consecutive failed reconnects. Recovery is restart-only.
  • One-time stderr warning at the threshold, regardless of debug flag.
  • Existing onError(err: Error) signature is unchanged — hosts narrow via instanceof.

Closes#22.

Wave 1 of the issue-waves roadmap (docs/superpowers/roadmap-2026-05-13-issue-waves.md); Sub-plan B for cross-SDK parity is tracked at recost-dev/middleware-python#32.

Branch contents

12 commits — 2 leading docs commits (roadmap + spec, then plan) ride at the head of the implementation branch by intent (combined PR rather than separate docs/impl PRs):

  • 856dce9 docs(roadmap): 6-wave issue plan + Wave 1 Sub-plan A spec
  • 1938601 docs(plan): WS terminal failure implementation plan
  • 3 setup feat commits (types, public-api export, ResolvedConfig wiring)
  • 1 bundled feat impl commit (TDD test + production code together)
  • 5 test commits (threshold trip, send-after-pause, counter reset, configurable threshold, cloud-mode-unaffected + idempotency)
  • 1 README docs commit

Test plan

  • npm run test — 235/235 green (228 baseline + 7 new cases)
  • npm run lint — clean
  • npm run build — clean dual ESM + CJS + DTS
  • Manually verify in a host process with no VS Code extension running: SDK stops spinning after the threshold, one stderr line is printed, one onError(RecostLocalUnreachableError) fires, CPU drops to zero.

- roadmap-2026-05-13-issue-waves.md: groups the 11 open issues into
six 2-issue waves with theme, files, ordering rationale, and
status placeholders. Tracking doc for the orchestrator.
- specs/2026-05-13-ws-terminal-failure-design.md: design for #22
(WebSocket reconnect terminal failure mode). Mirrors the #16
pattern shipped in PR #32: typed RecostLocalUnreachableError
through onError, threshold counter (default 20, reuses existing
_reconnectAttempts), one-shot stderr line, send() becomes
silent no-op once paused, restart-only recovery.
…#22)
12-task plan for Wave 1 Sub-plan A. Mirrors PR #32's structure:
3 setup tasks (types, exports, ResolvedConfig wiring), 1 TDD-red
task, 1 implementation+green task with bundled commit, 5 test
tasks (threshold trip, send-after-pause no-op, counter reset on
successful connect, configurable threshold, cloud-mode-unaffected
+ idempotency), 1 README docs task, 1 final verification + PR
task. Each test is calibrated to keep wall-clock under vitest's
default per-test timeout.
Roadmap also updated to reference middleware-python#32 (Sub-plan
B follow-up issue, filed separately).
@coderabbitai

Copy link
Copy Markdown

Warning

Rate limit exceeded

@AndresL230 has exceeded the limit for the number of commits that can be reviewed per hour. Please wait 17 minutes and 5 seconds before requesting another review.

You’ve run out of usage credits. Purchase more in the billing tab.

⌛ How to resolve this issue?

After the wait time has elapsed, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

We recommend that you space out your commits to avoid hitting the rate limit.

🚦 How do rate limits work?

CodeRabbit enforces hourly rate limits for each developer per organization.

Our paid plans have higher rate limits than the trial, open-source and free plans. In all cases, we re-allow further reviews after a brief timeout.

Please see our FAQ for further information.

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: 8744f10a-1a87-4263-b20e-b9fc0ea91cf9

📥 Commits

Reviewing files that changed from the base of the PR and between 3f28421 and d69cf4e.

📒 Files selected for processing (8)
  • README.md
  • docs/superpowers/plans/2026-05-13-ws-terminal-failure.md
  • docs/superpowers/roadmap-2026-05-13-issue-waves.md
  • docs/superpowers/specs/2026-05-13-ws-terminal-failure-design.md
  • src/core/transport.ts
  • src/core/types.ts
  • src/index.ts
  • tests/transport.test.ts
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feat/22-ws-terminal-failure

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 and usage tips.

@AndresL230
AndresL230 merged commit c38595e into mainMay 14, 2026
1 check passed
@AndresL230
AndresL230 deleted the feat/22-ws-terminal-failure branch May 21, 2026 04:15
Sign up for freeto 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.

WebSocket reconnect retries forever, no terminal failure mode

1 participant

@AndresL230
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Universal Dark Mode - works on any site\n(function() {\n var enabled = true;\n \n function applyDarkMode() {\n if (!enabled) return;\n \n // Create style element if it doesn't exist\n var style = document.getElementById('universal-dark-mode-style');\n if (!style) {\n style = document.createElement('style');\n style.id = 'universal-dark-mode-style';\n document.head.appendChild(style);\n }\n \n // Dark mode CSS - inverts colors but preserves images/video\n style.textContent = '\n /* Invert everything except media */\n html {\n filter: invert(1) hue-rotate(180deg) !important;\n background: #1a1a2e !important;\n }\n \n /* Restore images, videos, iframes, canvas */\n img, video, iframe, canvas, svg, picture, [style*=\"background-image\"] {\n filter: invert(1) hue-rotate(180deg) !important;\n }\n \n /* Preserve specific elements that should not be inverted */\n .no-dark-mode, .no-dark-mode *,\n [data-theme=\"light\"], [data-theme=\"light\"],\n .ace_editor, .ace_editor *,\n .CodeMirror, .CodeMirror *,\n .monaco-editor, .monaco-editor *,\n .markdown-body pre, .markdown-body pre *,\n .highlight, .highlight *,\n pre code, pre code * {\n filter: none !important;\n }\n \n /* Fix common UI elements */\n .modal, .popup, .dropdown-menu, .tooltip, .popover {\n filter: invert(1) hue-rotate(180deg) !important;\n background: #2d2d44 !important;\n border-color: #444 !important;\n }\n \n /* Scrollbars */\n ::-webkit-scrollbar { background: #1a1a2e !important; }\n ::-webkit-scrollbar-thumb { background: #444 !important; }\n ::-webkit-scrollbar-thumb:hover { background: #555 !important; }\n \n /* Selection */\n ::selection { background: #4ecdc4 !important; color: #1a1a2e !important; }\n ::-moz-selection { background: #4ecdc4 !important; color: #1a1a2e !important; }\n ';\n }\n \n function removeDarkMode() {\n var style = document.getElementById('universal-dark-mode-style');\n if (style) style.remove();\n }\n \n // Toggle with Alt+Shift+D\n document.addEventListener('keydown', function(e) {\n if (e.altKey && e.shiftKey && e.key === 'D') {\n e.preventDefault();\n enabled = !enabled;\n if (enabled) {\n applyDarkMode();\n console.log('[Universal Dark Mode] Enabled');\n } else {\n removeDarkMode();\n console.log('[Universal Dark Mode] Disabled');\n }\n }\n });\n \n // Apply on load\n applyDarkMode();\n \n // Re-apply on dynamic content\n var observer = new MutationObserver(function(mutations) {\n if (enabled && !document.getElementById('universal-dark-mode-style')) {\n applyDarkMode();\n }\n });\n observer.observe(document.head, { childList: true });\n \n console.log('[Universal Dark Mode] Loaded - Press Alt+Shift+D to toggle');\n})();", "Universal Dark Mode"); } } catch(__e) { console.warn('[Userscript:Universal Dark Mode]', __e); } })(); })();
Skip to content

feat: local-mode WS terminal failure — pause after N reconnects, typed error (#22) - #33

Merged
AndresL230 merged 12 commits into
mainfrom
feat/22-ws-terminal-failure
May 14, 2026
Merged

feat: local-mode WS terminal failure — pause after N reconnects, typed error (#22)#33
AndresL230 merged 12 commits into
mainfrom
feat/22-ws-terminal-failure

Conversation

@AndresL230

Copy link
Copy Markdown
Contributor

Summary

  • Adds RecostLocalUnreachableError to the public API; sibling to the RecostAuthError hierarchy added in PR feat: 401 auth-failure handling — suspend after N, typed errors (#16) #32.
  • Pauses the local WebSocket transport after maxConsecutiveReconnectFailures (default 20) consecutive failed reconnects. Recovery is restart-only.
  • One-time stderr warning at the threshold, regardless of debug flag.
  • Existing onError(err: Error) signature is unchanged — hosts narrow via instanceof.

Closes#22.

Wave 1 of the issue-waves roadmap (docs/superpowers/roadmap-2026-05-13-issue-waves.md); Sub-plan B for cross-SDK parity is tracked at recost-dev/middleware-python#32.

Branch contents

12 commits — 2 leading docs commits (roadmap + spec, then plan) ride at the head of the implementation branch by intent (combined PR rather than separate docs/impl PRs):

  • 856dce9 docs(roadmap): 6-wave issue plan + Wave 1 Sub-plan A spec
  • 1938601 docs(plan): WS terminal failure implementation plan
  • 3 setup feat commits (types, public-api export, ResolvedConfig wiring)
  • 1 bundled feat impl commit (TDD test + production code together)
  • 5 test commits (threshold trip, send-after-pause, counter reset, configurable threshold, cloud-mode-unaffected + idempotency)
  • 1 README docs commit

Test plan

  • npm run test — 235/235 green (228 baseline + 7 new cases)
  • npm run lint — clean
  • npm run build — clean dual ESM + CJS + DTS
  • Manually verify in a host process with no VS Code extension running: SDK stops spinning after the threshold, one stderr line is printed, one onError(RecostLocalUnreachableError) fires, CPU drops to zero.

- roadmap-2026-05-13-issue-waves.md: groups the 11 open issues into
six 2-issue waves with theme, files, ordering rationale, and
status placeholders. Tracking doc for the orchestrator.
- specs/2026-05-13-ws-terminal-failure-design.md: design for #22
(WebSocket reconnect terminal failure mode). Mirrors the #16
pattern shipped in PR #32: typed RecostLocalUnreachableError
through onError, threshold counter (default 20, reuses existing
_reconnectAttempts), one-shot stderr line, send() becomes
silent no-op once paused, restart-only recovery.
…#22)
12-task plan for Wave 1 Sub-plan A. Mirrors PR #32's structure:
3 setup tasks (types, exports, ResolvedConfig wiring), 1 TDD-red
task, 1 implementation+green task with bundled commit, 5 test
tasks (threshold trip, send-after-pause no-op, counter reset on
successful connect, configurable threshold, cloud-mode-unaffected
+ idempotency), 1 README docs task, 1 final verification + PR
task. Each test is calibrated to keep wall-clock under vitest's
default per-test timeout.
Roadmap also updated to reference middleware-python#32 (Sub-plan
B follow-up issue, filed separately).
@coderabbitai

Copy link
Copy Markdown

Warning

Rate limit exceeded

@AndresL230 has exceeded the limit for the number of commits that can be reviewed per hour. Please wait 17 minutes and 5 seconds before requesting another review.

You’ve run out of usage credits. Purchase more in the billing tab.

⌛ How to resolve this issue?

After the wait time has elapsed, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

We recommend that you space out your commits to avoid hitting the rate limit.

🚦 How do rate limits work?

CodeRabbit enforces hourly rate limits for each developer per organization.

Our paid plans have higher rate limits than the trial, open-source and free plans. In all cases, we re-allow further reviews after a brief timeout.

Please see our FAQ for further information.

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: 8744f10a-1a87-4263-b20e-b9fc0ea91cf9

📥 Commits

Reviewing files that changed from the base of the PR and between 3f28421 and d69cf4e.

📒 Files selected for processing (8)
  • README.md
  • docs/superpowers/plans/2026-05-13-ws-terminal-failure.md
  • docs/superpowers/roadmap-2026-05-13-issue-waves.md
  • docs/superpowers/specs/2026-05-13-ws-terminal-failure-design.md
  • src/core/transport.ts
  • src/core/types.ts
  • src/index.ts
  • tests/transport.test.ts
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feat/22-ws-terminal-failure

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 and usage tips.

@AndresL230
AndresL230 merged commit c38595e into mainMay 14, 2026
1 check passed
@AndresL230
AndresL230 deleted the feat/22-ws-terminal-failure branch May 21, 2026 04:15
Sign up for freeto 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.

WebSocket reconnect retries forever, no terminal failure mode

1 participant

@AndresL230