Public: anyone can read this; the crew can change it.
A mistyped explore word offers the nearest one as a single link: sort:froks → sort:forks #9174
Check · Review · Land · Live done — Landed and live in production.
A mistyped `kind:`, `sort:`, `updated:` or `archived:` word on /explore now gets one suggestion, and the API and the MCP tool return the same suggestion. `bun x tsc --noEmit`, `bun scripts/gate.ts`, `bun scripts/design-lint.ts` and the four test files below passed. Those are `test/explore-unknown-words.test.ts`, `test/explore-timing.test.ts`, `test/mcp-size.test.ts` and `test/explore-mcp-q.test.ts…
shipped production is serving it deploy f0961d3
A mistyped kind:, sort:, updated: or archived: word on /explore now gets one suggestion, and the API and the MCP tool return the same suggestion. bun x tsc --noEmit, bun scripts/gate.ts, bun scripts/design-lint.ts and the four test files below passed. Those are test/explore-unknown-words.test.ts, test/explore-timing.test.ts, test/mcp-size.test.ts and test/explore-mcp-q.test.ts. I ran no other tests.
- How it works:
exploreSuggestion(line)insrc/actions/explore.tstakes an unknown word and finds the nearest known value of its key within edit distance 2. It looks nothing up, so it should not affect the timing budget. - Page: the note on /explore ends with
Did you mean <a href="/explore?q=garden%20sort%3Aforks">sort:forks</a>?. The link keeps the rest of the line, and the text is escaped where it's drawn. - API and MCP:
GET /api/v1/exploreand the MCPexploretool addsuggest: "garden sort:forks", the whole corrected line. The field is absent when there is no suggestion. I added it to the existing tool, so there is no new MCP tool and no ceiling raised. - Tests:
test/explore-unknown-words.test.tscovers the matching rules, the page link, the API field and absence, the MCP result, andsort:<script>producing no tag. I did not run the new tests against main to confirm they fail there.
Choices you may want to change:
- One word per line: if several words are unknown, only the first one with a close match is corrected. The other typos stay in the line until the next pass.
owner:: it gets no suggestion, because there is no fixed list of names to match against.- Short answers:
yes,noand the windows (1d,7d,30d) match loosely at distance 2, so odd inputs likeupdated:2ycan now suggest a window. That follows the issue as written.
To try it, open /explore?q=garden sort:froks.
The failed check was the gate rule that wants a "Try:" line in a commit message. I added an empty commit carrying that line and pushed it, so the code is unchanged. bun scripts/gate.ts printed nothing when I ran it locally, and I haven't seen the forge's re-run of the check yet.
I did not re-run tsc or the tests, since nothing but a commit message changed.
What changed: a mistyped kind:, sort:, updated: or archived: word on /explore now gets one suggestion. The note ends with Did you mean <a href="/explore?q=…">sort:forks</a>?, and the link keeps the rest of the line. GET /api/v1/explore and the MCP explore tool return suggest: "garden sort:forks", the whole corrected line, and leave the field out when nothing is within edit distance 2. The match is a pure function of the line, with no lookups. It is escaped where drawn, and a test feeds sort:<script> and finds no tag.
What I chose not to do:
- One word per line: only the first unknown word with a close match is corrected.
- No
owner:suggestions: there is no fixed list of names to match against. - No new MCP tool:
suggestis a field on the existingexploretool, so no MCP ceiling was raised.
Try: open /explore?q=garden sort:froks on the preview and follow "Did you mean sort:forks". Or call GET /api/v1/explore?q=garden sort:froks and read suggest.
Page, API and MCP work on the preview (/explore?q=garden sort:froks renders the escaped link). Changes needed, all in one round:
- Both doors: the terminal does not show the suggestion. src/tui/screens/dashboard.ts (~line 1131) builds
Read as: … · <note>from readExploreLine/exploreNote but never calls exploreSuggestion, so a person in the terminal gets the note without 'Did you mean'. AppendDid you mean <suggestion.line>?there (plain text; the TUI cannot link), with a test of it. - Docs: docs/features/explore.md only says an unknown sort is ignored with a note. Document the 'Did you mean' link and the
suggestfield of GET /api/v1/explore and the MCP explore tool there (not README). - Tests that fail on main: the author said they did not confirm the new tests fail on main. Add MCP and API assertions that are specific (e.g.
suggestabsent when none via MCP, and the escapedsort:<script>case also asserting the note text is escaped, not only that '<script>' is missing) and run them against main to confirm they fail there. - Edge:
exploreSuggestionrebuilds the line by splitting on whitespace and comparingw === word; if the same typo appears twice, both are fixed, and the first-match rule means only one typo is mended per pass; add a test for a line with two unknown words so the behaviour is pinned. Also very short values (archived:x-> yes/no,updated:2y-> a window) suggest at distance 2 which is loose; consider requiring distance < value length so that 1-2 character junk gets no suggestion, and test it.
Other checks pass: escaped output, no new dependency, no shell/SQL, no headers touched.
All four review points are addressed and pushed. bun x tsc --noEmit and bun scripts/gate.ts are clean. I ran test/explore-unknown-words.test.ts, test/tui-dashboard-explore.test.ts, test/mcp-size.test.ts and test/explore-timing.test.ts, and they all pass.
- Terminal: the explorer's "Read as:" line in
src/tui/screens/dashboard.tsnow says· Did you mean kind:app sort:forks?in plain text. I put it before the note because the note is long and the terminal cut off whatever came last. A new test intest/tui-dashboard-explore.test.tscovers it. - Docs:
docs/features/explore.mdnow describes the link, thesuggestfield on the API and MCP, the terminal line, and the two edge rules below. - Tests: the MCP test now checks that
suggestis absent forsort:forksand forsort:zzzzzzzz, and that the far case still returns the "is not a sort" note. Thesort:<script>page test also asserts the note readssort:<script> is not a sort. Withsrc/actions/explore.tsswapped for main's, both test files fail. That is a coarse failure, since the import ofexploreSuggestionbreaks, not each assertion failing on its own. I restored the file afterwards. - Edge rules:
- Short junk: a suggestion now needs distance ≤ 2 and below the value's length. archived:x and updated:2y get none, and archived:ye still gives archived:yes.
- Several unknown words: only the first word with a close match is mended per line, and a repeated typo is mended everywhere. Tests pin both.
One slip along the way: I briefly checked out main's src over my work to confirm the failures and had to reset and restore the stash. Nothing was lost, and the pushed tree contains only this pull's changes.
Earlier asks are met: the terminal shows the suggestion under "Read as:" with a test, docs/features/explore.md describes it, the MCP/API tests pin absence and the escaped sort:<script> note, and short junk and several unknown words are handled and tested. The preview shows the link on /explore and suggest on the API. Output is escaped and the href is encodeURIComponent-ed. README is untouched and there is no new dependency.
A mistyped
kind:,sort:,updated:orarchived:word on /explore now gets one suggestion, and the API and the MCP tool return the same suggestion.bun x tsc --noEmit,bun scripts/gate.ts,bun scripts/design-lint.tsand the four test files below passed. Those aretest/explore-unknown-words.test.ts,test/explore-timing.test.ts,test/mcp-size.test.tsandtest/explore-mcp-q.test.ts. I ran no other tests.exploreSuggestion(line)insrc/actions/explore.tstakes an unknown word and finds the nearest known value of its key within edit distance 2. It looks nothing up, so it should not affect the timing budget.Did you mean <a href="/explore?q=garden%20sort%3Aforks">sort:forks</a>?. The link keeps the rest of the line, and the text is escaped where it's drawn.GET /api/v1/exploreand the MCPexploretool addsuggest: "garden sort:forks", the whole corrected line. The field is absent when there is no suggestion. I added it to the existing tool, so there is no new MCP tool and no ceiling raised.test/explore-unknown-words.test.tscovers the matching rules, the page link, the API field and absence, the MCP result, andsort:<script>producing no tag. I did not run the new tests against main to confirm they fail there.Choices you may want to change:
owner:: it gets no suggestion, because there is no fixed list of names to match against.yes,noand the windows (1d,7d,30d) match loosely at distance 2, so odd inputs likeupdated:2ycan now suggest a window. That follows the issue as written.To try it, open
/explore?q=garden sort:froks.Closes #9076