How Search Works
When an operator types in the search bar, Forest sends a query to your back-end with the search string. The back-end applies it as a filter against your data source and returns matching records. Two search modes exist:- Normal search, searches fields in the current collection
- Extended search, also searches fields in directly related collections. Operators can trigger extended search from the footer when normal results are empty.
read permission. From version 1.97.3 on, the agent refuses an extended search whose fields it cannot enumerate ahead of the query. This governs how you replace the search handler — see Replacing the Search Handler.
Default Search Behavior
By default, Forest searches only specific field types:Replacing the Search Handler
UsereplaceSearch in your back-end configuration to define exactly how search strings are translated into filters.
The Node.js agent accepts two forms, and they differ in what extended search does:
Reach for a field selection whenever the fields are a fixed list. Reach for a handler when the filter depends on the search string itself, on an external service, or on anything else a list cannot express — and accept that extended search stops working on that collection.
For large datasets, limit searchable fields to columns with database indexes. Searching unindexed fields causes full table scans.
The field selection form exists in Node.js only. In Python, the handler receives a
context with the generate_search_filter helper. In Ruby, the replace_search block receives (search_string, extended_search) and returns a condition tree directly: there is no generate_search_filter helper, so you build the tree yourself. The Ruby and Python agents do not refuse extended search on a collection with a handler.Restricting Which Fields Are Searched
Excluding Fields from Default Search
includeFields, which adds fields to the default set instead of replacing it. Paths cross relations with a colon, at any depth: includeFields: ['company:owner:email']. The agent checks the collection each path ends on — companies confers nothing here, users needs the read permission. A path crossing a ManyToMany relation does not resolve and is dropped from the selection without an error; ManyToOne, OneToOne and OneToMany segments all resolve.
A field selection narrows the fields on normal search as well as extended search, so the fields it names are checked against the operator’s
read permission on both. An operator who searches people without read on a collection an included path ends on receives a 403 where a handler returned results. Grant that permission, or drop the path from the selection.Context-Dependent Search
Different search logic depending on what the operator is searching for. This needs a handler, so extended search returns 403 on the collection:Integrating an External Search Engine
If your data is indexed in Algolia, Elasticsearch, or another service, call it directly in the search handler. Extended search returns 403 on such a collection in Node.js, since the agent cannot know which columns the external index reads:Disabling Search
To remove the search bar from a collection entirely:Limitations
A handler gives up extended search in Node.js. A field selection is the only form the agent can enumerate, so it is the only form that keeps extended search on the collection. A handler whose filter genuinely depends on the search string, on an external index, or on a runtime lookup has no equivalent field selection, and extended search stays refused there. Normal search is unaffected. A field selection replaces a datasource’s native search. On a collection whose datasource searches natively — one callingenableSearch(), which no Forest-maintained datasource does — a field selection does not narrow that native search: the agent takes the search over and runs its own per-column one on the selected fields. Matching semantics change with it.
Version requirements. The refusal starts at @forestadmin/agent 1.97.3. The field selection form requires @forestadmin/datasource-customizer 1.71.3, shipped in @forestadmin/agent 1.98.3.
Agents differ. The table below states where each behavior applies today:
A handler is exempt from read permissions on normal search. The operator supplies the text and the handler chooses the fields, so the agent cannot separate a field the customization intended from one the operator’s role may not read. A handler pointing at a column of a collection the role cannot read lets that role test values against it, reading each answer from whether rows come back. Prefer a field selection wherever the fields are a fixed list.