Explain a Backend URL/page-origin mismatch instead of a bare fetch error
A real Windows install had sync and backups fail everywhere with "Failed to fetch" while the server itself was fully healthy - confirmed via Invoke-WebRequest returning 200 for every endpoint the browser couldn't reach. The page was opened via a LAN IP while Settings still had the Backend URL set to 127.0.0.1 from an earlier session; browsers treat those as different origins, so the server's CORS check correctly rejected the requests, but a CORS rejection surfaces to fetch() as an unexplained generic error with no indication of the real cause. Settings now detects this mismatch on every render and shows the page's actual address with a one-click button to fix it. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
This commit is contained in:
@@ -46,8 +46,11 @@ Acceptance: users can distinguish server contact, pending edits, an active save
|
||||
- [x] Offer manual retry for unsaved changes without discarding local edits.
|
||||
- [x] Verify save failure/reconnection in a real browser.
|
||||
- [x] Extend stale-data feedback to the personal mobile profile: last applied retrieval, 30-second stale warning, timeout and Retry without discarding loaded data.
|
||||
- [x] Detect and explain a Backend URL/page-origin mismatch, the real cause behind an otherwise unexplained "Failed to fetch" on every sync and backup.
|
||||
- [ ] Review concurrent writes, reconnect recovery and multiple controllers editing the same race.
|
||||
|
||||
Fixed 2026-09-09: a real Windows install showed "Backup failed: Sync failed: Failed to fetch" and every other backend call failing the same way, while the server itself was healthy (confirmed via `Invoke-WebRequest` returning 200 for `/api/health`, `/api/state` and `/api/backups`) - only the browser's own `fetch()` calls failed. Root cause: the page was opened via the LAN IP (`http://192.168.1.100:8081`) while the persisted Settings "Backend URL" still said `http://127.0.0.1:8081` from an earlier session. Browsers treat those as different origins even on the same machine, so the server's CORS check (`server.js`, comparing the request's `Origin` header against its own `Host` header) correctly rejected it - but nothing told the user why, since a CORS-rejected response surfaces to `fetch()` as a generic "Failed to fetch" with no further detail, and a command-line tool like `Invoke-WebRequest` doesn't send an `Origin` header at all, so it never reproduced the symptom. The Settings page now compares `window.location.origin` against the configured Backend URL on every render and, when they differ, shows a plain-language warning naming the page's actual address plus a one-click "Use `<address>`" button that fixes it immediately. Verified with a headless-browser check (seeding a deliberately mismatched Backend URL, confirming the warning text names the real origin, and confirming the fix button both clears the warning and persists the corrected value to the backend) against an isolated temp SQLite instance.
|
||||
|
||||
### Implemented: decoder/socket diagnostics
|
||||
|
||||
Acceptance: each configured channel distinguishes an open socket from actual received data and successfully parsed passing messages. Inspecting diagnostics must not interrupt timing or rerender an active settings form.
|
||||
|
||||
Reference in New Issue
Block a user