Search
Help users find records by what they remember — a name, a number, a phrase — with results that explain why they matched.
5 states5 edge casesDesktop + Mobile
01The problem
Users remember fragments: part of a customer name, an invoice number, a phrase from a comment. If search only matches exact titles, misses typos, or returns a flat list without context, users give up and browse manually. Search also has to coexist with filters without confusing users about which one is narrowing the results.
02When to use
Use when
- Products with more records than users can browse
- Lists where users look up specific items by name or number
- Content-heavy products: docs, tickets, conversations
Avoid when
- Small, stable lists — browsing is faster.
- Navigation between product areas — use a command palette.
03Recommended UX
Statecraft recommendation
Put search where the results will appear, match on everything users might remember (names, numbers, emails, content) with typo tolerance, and show why each result matched by highlighting the matching text. Keep the query in the URL and combine it visibly with any active filters.
Search in the list toolbar makes scope obvious: it searches this list, with these filters.
Highlighted matches let users verify results without opening them — especially when the match is in a secondary field like an email.
Queries in the URL make results shareable and survive Back.
04Interaction flow
- 01
Focus search
Recent searches shown when empty.
- 02
Type
Results update after a short debounce.
- 03
Scan results
Matches highlighted; secondary match fields shown.
- 04
Refine
Combine with filters or scope.
Result
- Opened result
- No results
- Refined
05Desktop behaviour
On desktop, search lives in the list toolbar. Results replace the list in place and keep the same row layout.
Desktop rules
- Shortcut “/” focuses the search field.
- Debounce ~200 ms; keep previous results visible while loading.
- Highlight matches in titles and show the matching secondary field: “Matched email: dana@lumen.de”.
- Show query and filters together: “12 results for ‘acme’ in Overdue invoices”.
06Mobile behaviour
On mobile, search opens a focused full-screen view with recent searches, then shows results as compact rows.
Mobile rules
- Tap search to open a full-screen view with the keyboard up.
- Recent searches and suggestions before typing.
- Results as compact rows with highlighted matches; Cancel returns to the list.
07States
Empty focus
Recent searches and suggestions.
Typing
Debounced; previous results dimmed while loading.
Results
Count, highlighted matches, match reason.
No results
Names the query and filters; offers to search everywhere.
Error
Search failed; Retry; query kept.
08Edge cases
EC-01
Typos
The user types “Stark Industires”.
Recommendation
Use fuzzy matching and show “Showing results for Stark Industries”.
EC-02
Exact identifiers
The user pastes “INV-1024”.
Recommendation
Detect ID-shaped queries and put the exact match first — or jump straight to it.
EC-03
Search plus filters return nothing
“acme” finds nothing in Paid invoices but 4 in Overdue.
Recommendation
Say so: “No results in Paid. 4 results in all invoices.”
EC-04
Results the user can't open
A match is in a private project.
Recommendation
Exclude it from results entirely; search must respect permissions.
EC-05
Stale responses
A slow response for “ac” arrives after the one for “acme”.
Recommendation
Cancel or ignore out-of-date requests.
09Microcopy
Placeholder
Avoid
“Search…”
Prefer
“Search by name, number or email”
Result count
Prefer
“12 results for “acme” in Overdue invoices”
Typo
Prefer
“Showing results for Stark Industries”
No results
Avoid
“No matches”
Prefer
“No results in Paid. 4 results in all invoices.”
10Accessibility
- Search input has a visible or accessible label and role="search" on its container.
- Announce result counts politely after typing pauses.
- Highlights use <mark>, which carries meaning beyond colour.
11Developer notes
- 01
Use a search index with typo tolerance and per-field weighting (title > identifier > secondary fields > content).
- 02
Apply permissions inside the search query, not by filtering after retrieval.
- 03
Return highlight ranges from the server.
- 04
Keep the query in the URL alongside filters.
12Implementation prompt
For Claude Code, Codex or Cursor
Implement search for the existing list views. Requirements: - Search field in the list toolbar (role="search", labelled), "/" shortcut. - Debounced queries (~200 ms); cancel stale requests; keep previous results dimmed while loading. - Indexed search with typo tolerance and field weighting; exact ID matches first. - Permissions applied in the query. - Highlighted matches (<mark>) with secondary match field shown. - Count with scope: "12 results for 'acme' in Overdue invoices". - No-results state suggests broader scope with counts. - Query in URL with filters; recent searches on empty focus. - Mobile: full-screen search with recents; compact result rows. Do not redesign the existing interface.