fix(webapp): a bogus project deep link says so instead of swapping projects (BEA-83) - #131
Open
ssowonny wants to merge 1 commit into
Open
Conversation
…ojects (BEA-83) /no-such-project-xyz/some/file.md used to redirect to whichever project the fallback chain picked, dropping the path — nothing on screen distinguished "that link is wrong" from "you opened your project." An unknown route.project now renders a "Project not found" panel at the URL as typed, mirroring the org-not-found page two blocks up: shell, sidebar and account bar stay mounted, and "Back to <name>" points at the same project the fallback picks today. The fallback chain itself is unchanged, and "/" still redirects to the remembered project (BEA-75). All four redirects below the flag rewrite the address bar off current.id, so they are gated together — /bad-id/insights and /bad-id/notes/ would otherwise undo the fix on their own. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
TL;DR
/still lands on the remembered project (BEA-75 unchanged).projectslist and reads as not-found until the next refresh.One
ifwas serving two cases that want opposite answers:flowchart TD R["route.project"] R -->|"'' — landing on /"| A["redirect to the remembered project<br/>✅ correct, this is BEA-75"] R -->|"an id not in your list"| B["redirect to the fallback project<br/>❌ wrong project, path dropped"] B -.->|this PR| C["render 'Project not found'<br/>at the URL as typed"]Reproduced on
origin/mainbefore touching anything —/no-such-project-xyz/some/file.mdended up at/30d8fa88-…showing thewikihome.What changed
internal/webapp/frontend/src/apps/HubApp.tsx, ~20 lines:orgMissing:projectMissing = !!route.project && !projects.some(p => p.id === route.project).routePageso/bad-id/settingsrenders not-found rather than the fallback project's settings.!projectMissing.The copy deliberately does not distinguish "doesn't exist" from "you're not a member" —
/api/projectsonly ever returns your orgs' projects, so the SPA genuinely can't tell, and a page that could would answer "does this id exist on this hub?" for anyone who asked. Same sentence as the org page.Deviations from the reviewed plan
Both are small, but the plan said otherwise, so they're called out rather than buried:
:265,:272,:280)queryTarget(/bad-id/history?path=x) also rewrites offcurrent.id. All four now sit inside oneif (!projectMissing)block, so a fifth can't be added without inheriting the guard.hub.spec.ts:207and:220need checkinghub.spec.ts:25— "unknown project id falls back to a real project" — asserted the exact behavior this issue calls a bug. Rewritten to the new expectation (URL preserved, not-found shown, sidebar still on a real project). The plan didn't mention it.Screenshots
Same request in both:
GET /no-such-project-xyz/some/file.md, signed in ase2e@example.com.wikihome, URL rewritten to/30d8fa88-…, path gone/no-such-project-xyz/some/file.md(Playwright screenshots are viewport-only, so the address bar isn't in frame — the URL is asserted in the specs instead.)
What can't break
/still redirects.route.project === ""makesprojectMissingfalse, so BEA-75's landing behavior is bit-for-bit unchanged. Its two specs pass untouched.currentresolves to exactly the project it did before; it just stops being shown silently under someone else's URL./orgs/<id>and/billingare exempt, as before — neither is project-scoped.rememberProjectunchanged. It writescurrent.id, and the id it writes is always one the viewer is a member of.What was run
go build ./...,go vet ./...,go test ./...— all packages pass.npm run e2e— 154 passed, 1 skipped, 0 failed, including the new case and the two BEA-75 specs.npm test(frontend units) — 57 pass.npm run build+check-dist.sh—internal/webapp/staticcommitted and fresh.browse.spec.tscovers the bullets plus a reload (no bounce, no loop) and the/insightsand/notes/rewrites that would otherwise undo the fix.The one thing left open
A project created on another device sits outside a stale
projectslist, so its URL reads as not-found until the list refreshes. The spec accepts this rather than paying a server round-trip on every unknown id —projectsrefreshes on navigation and the sidebar recovers it. Worth a second look if anyone hits it in practice; it's the only false positive this change can produce.Closes BEA-83.
Build session
(only works on the machine that ran the build)