The web app has one search engine that finds apps, settings pages, app screens, actions, and records. It opens as an overlay over the home screen and is also embedded in the Apps library. This page lists the result families, the mode prefixes, the keyboard use, how records are queried, and how recent picks are kept. The server-side search helpers are on search, pagination, and bulk operations.
Scope and source¶
- Defined in:
webapp/js/home.js(openSpot,runSearch,searchableEntities,rowContainsQuery,settingsSearchTargets),webapp/js/search-index.js(screenTargets,actionTargets,matchTargets,SPOT_MODES,parseSpotQuery) - Count: 6 result families (recent, apps, settings, screens, actions, records) and 5 mode prefixes (
SPOT_MODES,webapp/js/search-index.js:163-169)
Opening the palette¶
| Entry | Source |
|---|---|
| Search button on the home status line | webapp/js/home.js:151 |
| Downward swipe on the home screen | webapp/js/home.js:4446-4453 |
| Ctrl+K, or Cmd+K on Apple platforms, from anywhere | webapp/js/home.js:4363-4370, webapp/js/home.js:1138-1142 |
| The search field of the Apps library, debounced by 200 ms | webapp/js/home.js:2644-2659 |
The overlay shows a hint bar with the open shortcut, every mode prefix, and the arrow and Enter keys (webapp/js/home.js:1143-1152). Arrow keys move the highlight and Enter opens it (webapp/js/home.js:4329-4337). Typing is debounced by 220 ms before a query runs (webapp/js/home.js:4340-4343).
Result families¶
| Family | Source of targets | Match rule | Limit | Source |
|---|---|---|---|---|
| Recent | The user's last picks | Title or subtitle contains the query | 8 kept | webapp/js/home.js:1135-1157, webapp/js/home.js:1406-1424 |
| Apps | Installed apps from the registry | Label contains the query | none | webapp/js/home.js:1426-1431 |
| Settings | settingsRows() rows with an open handler, plus admin entity screens |
Label contains the query | none | webapp/js/home.js:3517-3527, webapp/js/home.js:1432-1438 |
| Screens | Every sidebar section of installed module apps, and every tab of their settings sections | matchTargets |
12 | webapp/js/search-index.js:30-71, webapp/js/home.js:1440-1442 |
| Actions | Every ActionMeta and record_actions entry of entities the user may read |
matchTargets |
12 | webapp/js/search-index.js:78-127, webapp/js/home.js:1443-1445 |
| Records | Live list queries of searchable entities | Server search, then a client check | 6 per entity | webapp/js/home.js:1235-1276, webapp/js/home.js:1375-1396 |
matchTargets(targets, query) requires every word of the query in the title or subtitle. A one-word query must match the title. Results whose title starts with the first word rank first, then results that contain every word in the title (webapp/js/search-index.js:134-155).
Mode prefixes¶
A leading sign narrows the palette to one family (webapp/js/search-index.js:157-176).
| Prefix | Family | Label key |
|---|---|---|
> |
Actions | spotlight.actions |
/ |
Screens | spotlight.screens |
@ |
Apps | spotlight.apps |
? |
Settings | spotlight.settings |
# |
Records | spotlight.records |
Record search¶
searchableEntities() collects entities whose list view has search_enabled and whose <entity_type>.read permission the user holds. It covers the entity of each installed list app, the list, tree, and tabbed_list sections of installed module apps, and the admin entities of the auth module (webapp/js/home.js:1235-1276). For each entity the palette calls GenApi.list with search and limit: 6, in parallel (webapp/js/home.js:1538-1575).
The server applies search on each list endpoint; see search, pagination, and bulk operations. There is no central search endpoint: the client queries list endpoints one by one. rowContainsQuery keeps only rows in which a shallow string value contains the query, so an endpoint that ignores search cannot add unrelated rows (webapp/js/home.js:1369-1396). A row without a human title is left out (webapp/js/home.js:1278-1282, webapp/js/home.js:1557-1561). A 401 or 403 answer drops that entity silently; other failures are logged to the console (webapp/js/home.js:1567-1573).
A newer query cancels the display of older answers through a sequence number (webapp/js/home.js:1404, webapp/js/home.js:1576).
Opening a result¶
| Kind | Effect | Source |
|---|---|---|
| App | Opens the app | webapp/js/home.js:1466 |
| Settings | Opens the Settings app and pushes the settings screen | webapp/js/home.js:1284-1291 |
| Screen | Opens the app and switches to the section; a settings tab target opens that tab once | webapp/js/home.js:1296-1310, webapp/js/gen-settings.js:20-25 |
| Action | Opens the screen where the action lives; the user then picks a record | webapp/js/search-index.js:73-77, webapp/js/home.js:1296-1310 |
| Record | Opens the record card in its app | webapp/js/home.js:1312-1332 |
Recent picks¶
Each opened result is stored at the front of the recent list, at most 8 entries, under the UI-state key spot_recent (webapp/js/home.js:1135-1157). A recent entry is re-checked against what is installed and permitted before it is shown; an entry whose target is gone is skipped (webapp/js/home.js:1157-1191). An empty query shows only the recent section (webapp/js/home.js:1420-1424).
Constraints and validation¶
- The index is built at query time from the live catalogue and metadata; nothing is cached between queries (
webapp/js/search-index.js:8-15). - Search is language-aware: matching uses
toLocaleLowerCasewith the current language (webapp/js/search-index.js:21-22). - Browser tests:
web-client/_e2e_universal_search.mjs,web-client/_e2e_command_palette.mjs,web-client/_e2e_search.mjs,web-client/_e2e_library_search.mjs,web-client/_e2e_widgets_spot.mjs.
Terms introduced¶
| Term | Code identifier | Definition | Turkish term | Source |
|---|---|---|---|---|
| command palette | openSpot |
The search overlay that finds apps, settings, screens, actions, and records. | komut paleti | webapp/js/home.js:1121 |
| mode prefix | SPOT_MODES |
A leading sign that narrows the palette to one result family. | mod öneki | webapp/js/search-index.js:163 |
| search target | screenTargets |
A navigable place derived from metadata that the palette can open. | arama hedefi | webapp/js/search-index.js:30 |
Related pages¶
- Web app platform
- Home screen, dock, and launcher
- Module apps and app scope
- Search, pagination, and bulk operations
- User UI state
Verified against commit 92f8051 on 2026-11-13.