Search API
Implement search using Drupal Search API.
You need to install the JSON:API Search API module to query your Search API indexes.
Installation
- Start by installing the Search API module. If you want faceted search, install the Facets module as well.
composer require drupal/search_api drupal/facets drupal/jsonapi_search_api drupal/jsonapi_search_api_facets
- Enable the following modules: Search API, Database Search, Facets, JSON:API Search API and JSON:API Search API Facets.
- Create a server and index by following the guide here.
For every index created, a facet source is available. You can use this source to create filters.
- Visit
/admin/config/search/facets
and click on Add facet. - Under Facet source, select the server created above. For Field, select the field to filter on. Save.
- Next, edit the facet and make sure JSON:API Search API is selected under widget.
- You can now make queries to your indexes via JSON:API.
import { drupal } from "lib/drupal"
const results = await drupal.getSearchIndex(indexName, { params: { filter: { name_of_field: value }, },})
Implementation
We recommend using an API route for querying the search index. Using an API route means you can share search indexes, implement rate limiting and filtering using middlewares.
- Create the following API route.
api/pages/[index].tsx
import { NextApiRequest, NextApiResponse } from "next"import { DrupalNode } from "next-drupal"
import { drupal } from "lib/drupal"
export default async function handler( request: NextApiRequest, response: NextApiResponse) { try { const body = JSON.parse(request.body)
const { index } = request.query
const results = await drupal.getSearchIndex<DrupalNode>( index as string, body )
response.json(results) } catch (error) { return response.status(400).json(error.message) }}
- To make a search request from your React component, you can use a simple fetch request.
const response = await fetch("/api/search/INDEX-NAME-HERE", { method: "POST", body: JSON.stringify({ params: { filter: { name_of_field: value }, }, }),})
Localized Search Results
Next.js API Routes have no context of the current locale. For localized search results, you should pass the locale
and defaultLocale
from the router.
const router = useRouter()
const response = await fetch("/api/search/INDEX-NAME-HERE", { method: "POST", body: JSON.stringify({ params: { filter: { name_of_field: value }, }, locale: router.locale, defaultLocale: router.defaultLocale, }),})
Demo
See https://example-search-api.next-drupal.org.
Example
See https://github.com/chapter-three/next-drupal/tree/main/examples/example-search-api