Skip to content

fix: return 503 when Meshtastic node is not connected (traceroute and mesh requests)#3597

Merged
Yeraze merged 2 commits into
mainfrom
claude/great-dijkstra-1vnb5n
Jun 21, 2026
Merged

fix: return 503 when Meshtastic node is not connected (traceroute and mesh requests)#3597
Yeraze merged 2 commits into
mainfrom
claude/great-dijkstra-1vnb5n

Conversation

@Yeraze

@Yeraze Yeraze commented Jun 21, 2026

Copy link
Copy Markdown
Owner

Summary

Fixes #3596

When the Meshtastic node is disconnected, sendTraceroute (and all other meshRequestRoutes handlers) threw Error: Not connected to Meshtastic node which was caught and blindly re-emitted as a generic 500 { error: 'Failed to send traceroute' }. The frontend had no way to tell the user what actually went wrong.

  • Detect "Not connected" errors in the catch block of all five route handlers (/traceroute, /position/request, /nodeinfo/request, /neighborinfo/request, /telemetry/request) and return 503 with the message "Not connected to Meshtastic node" — matching the pattern already used in src/server/routes/v1/messages.ts.
  • Added two regression tests (traceroute and position request) that verify the 503 response.

Test plan

  • Existing 13 tests in meshRequestRoutes.test.ts still pass
  • Two new 503 tests pass
  • Manually: disconnect the Meshtastic source, attempt a traceroute — UI should now see a 503 with a clear "not connected" message instead of a generic error

🤖 Generated with Claude Code

https://claude.ai/code/session_01C3W1sLHSwNrrUzDQutFnyy


Generated by Claude Code

Traceroute (and position/nodeinfo/neighborinfo/telemetry) requests threw
a generic 500 when the node wasn't connected, hiding the real cause from
the UI. Now the catch block detects "Not connected" errors and returns 503
with an actionable message, matching the pattern already used in
src/server/routes/v1/messages.ts.

Fixes #3596

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01C3W1sLHSwNrrUzDQutFnyy
@github-actions

github-actions Bot commented Jun 21, 2026

Copy link
Copy Markdown

Claude encountered an error —— View job


I'll analyze this and get back to you.

@github-actions

github-actions Bot commented Jun 21, 2026

Copy link
Copy Markdown

Claude finished @Yeraze's task —— View job


PR Review

  • Read changed files
  • Check pattern consistency with existing code
  • Evaluate test coverage
  • Post review feedback

Summary

This is a clean, focused fix that correctly propagates connection errors as 503 responses. The implementation is solid. A few observations:

Strengths

  • Correctly applies the pattern across all five route handlers — no handler was missed
  • String check error?.message?.includes('Not connected') uses safe optional chaining, matching the existing pattern in messages.ts:564
  • Tests are well-structured and validate the new behavior

Minor Observations

1. Slight response shape inconsistency with messages.ts

messages.ts:565–569 returns a richer 503 body:

{ "success": false, "error": "Service Unavailable", "message": "Not connected to Meshtastic node" }

This PR returns a simpler shape across all five handlers:

{ "error": "Not connected to Meshtastic node" }

This inconsistency is minor, but if the frontend checks error vs message fields differently, it could cause subtle handling differences. Not a blocker, but worth noting for uniformity.

2. Test coverage gap: 3 of 5 handlers lack 503 tests

Tests were added for /traceroute and /position/request, but the other three handlers (/nodeinfo/request, /neighborinfo/request, /telemetry/request) don't have corresponding 503 regression tests. For /neighborinfo/request, the error could throw after the eligibility/rate-limit checks, which is worth covering.

3. String matching is fragile

The includes('Not connected') check works for the known error text, but a future refactor that changes the error message would silently regress back to 500. A more robust approach would be a typed/custom error class or error code — though this matches the existing project pattern, so it's consistent.

Verdict

The fix is correct and consistent with the existing codebase pattern. The two minor gaps (response shape inconsistency and incomplete test coverage) are non-blocking but worth addressing if polish is desired before merging.

…lers

Addresses review feedback on the "503 when not connected" fix:

1. The five mesh-request handlers now return the same 503 body shape as
   v1/messages.ts — { success: false, error: 'Service Unavailable',
   message: 'Not connected to Meshtastic node' } — instead of a bare
   { error: '...' }. The api.ts callers (sendTraceroute/requestPosition)
   read `error.message || error.error` so the specific reason still
   surfaces (they previously read only `.error`, which would otherwise
   have regressed to showing "Service Unavailable").

2. Add 503 regression tests for the three previously-uncovered handlers
   (/nodeinfo/request, /telemetry/request, and /neighborinfo/request —
   the latter failing after the eligibility/rate-limit checks).

Also adds the missing CHANGELOG entry for #3596.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01SVGxkuD4Fwa2JGVim8ZeVj
@github-actions

github-actions Bot commented Jun 21, 2026

Copy link
Copy Markdown

Claude encountered an error —— View job


I'll analyze this and get back to you.

@github-actions

github-actions Bot commented Jun 21, 2026

Copy link
Copy Markdown

Claude finished @Yeraze's task —— View job


PR Review

  • Read changed files
  • Check pattern consistency with existing code
  • Evaluate test coverage
  • Post review feedback

Summary

This is a clean, focused fix. The implementation is correct and complete. Here's the full review:

Code Quality — meshRequestRoutes.ts

Pattern consistency: ✅ Excellent. The 503 response shape used in this PR:

{ "success": false, "error": "Service Unavailable", "message": "Not connected to Meshtastic node" }

matches exactly the shape in src/server/routes/v1/messages.ts:564–569. This is the right call — the previous review noted an inconsistency, but this PR correctly mirrors the existing v1 pattern.

Error detection: ✅ Consistent. error?.message?.includes('Not connected') with optional chaining matches the pattern in messages.ts:564. Safe and idiomatic for this codebase.

Coverage: ✅ All five handlers handled. /traceroute, /position/request, /nodeinfo/request, /neighborinfo/request, and /telemetry/request all have the check.

Test Coverage — meshRequestRoutes.test.ts

503 tests: ✅ All five handlers covered. The updated PR now includes 503 regression tests for every handler:

  • /traceroute (line 76)
  • /position/request (line 100)
  • /nodeinfo/request (line 119)
  • /neighborinfo/request (line 161) — correctly tests the case where the error fires after the eligibility/rate-limit checks pass, with a unique destination to avoid rate-limit map bleed
  • /telemetry/request (line 204)

The /neighborinfo/request test is particularly well thought out — it uses a fresh destination num (0x0000cccc) to avoid cross-test contamination from the module-level neighborInfoRequestTimestamps map.

Frontend — api.ts

Change at line 704: The updated error extraction error.message || error.error || 'Failed to send traceroute' correctly prefers the specific message field (which carries "Not connected to Meshtastic node") over the generic error reason field. This means the frontend will surface the human-readable message to the user rather than "Service Unavailable". The same pattern is used at line 727 for requestPosition.

Minor note: Only sendTraceroute and requestPosition in api.ts were updated with the error.message || error.error priority order. Other frontend callers like requestNodeInfo, requestNeighborInfo, and requestTelemetry (if they exist) would also benefit from the same field-priority fix. Not a blocker, just worth checking whether those callers exist and extract errors the same way.

No Issues Found

  • No security concerns
  • No performance issues
  • No data leaks or unhandled rejection paths
  • The duplicate error detection pattern (string matching on includes('Not connected')) is fragile in the abstract, but this is the established project convention — adding a custom error class would be a separate refactor

Verdict

Ready to merge. The previous review's gaps (incomplete 503 test coverage, response shape mismatch) have both been addressed in this update. The fix is correct, consistent, and well-tested.

--- | Branch: claude/great-dijkstra-1vnb5n

@Yeraze Yeraze merged commit 6187328 into main Jun 21, 2026
20 of 21 checks passed
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.

[BUG] 4.11.2 - Error on Traceroute ....

2 participants