Skip to main content

Search (Elasticsearch)

The website search is powered by Elasticsearch via the elastic-search-with-i18n Strapi plugin. Content is automatically indexed when published in Strapi, and search is exposed through a custom API endpoint consumed by the frontend.


How It Works​

  1. When content is published in Strapi, the plugin indexes the configured fields into an Elasticsearch index.
  2. The frontend sends the user's query to /api/elastic/search?query=...&language=en.
  3. The CMS controller builds an Elasticsearch query and returns the matching documents.
  4. The frontend groups results by content type and displays them in tabs.

Indexed Content Types​

Only content types with "index": true on at least one field are active in search. The table below lists the searchable content types and their indexed fields.

Content TypeIndexed Fields
api::product.productmodelName, description, slug, product_series, featuredImage, excerpt, seo
api::product-category.product-categoryname, slug, description, excerpt, family, reasonsToBelive, seo
api::blog-post.blog-posttitle, slug, featuredImage, resourceCategories, resourceDate, resourceAuthor, content, resourcesCta, seo
api::news-article.news-articletitle, slug, featuredImage, resourceCategories, resourceDate, content, resourcesCta, seo
api::event.eventtitle, slug, featuredImage, resourceCategories, eventDate, eventLocation, content, resourcesCta, seo
api::testimonial.testimonialtitle, slug, featuredImage, resourceCategories, resourceDate, resourceAuthor, content, resourcesCta, seo
api::video.videotitle, slug, description, type, videoFile, videoThumbnail, youtubeID, resourceCategories
api::training.trainingtitle, slug, description, type, videoFile, videoThumbnail, youtubeID, resourceCategories
api::faq.faqtitle, content, faqs_category
api::faqs-category.faqs-categorytitle, slug, description, faqs
api::content-page.content-pagetitle, slug, description, frontendTitle, hero, content, featuredImage, seo
api::contacts-page.contacts-pagetitle, description, email, contactCards, content, seo

Note: Fields such as locale, localizations, and most relational/spec fields are not indexed and will never appear in search results.


Query Fields & Relevance Weights​

When a search is performed, the query runs a multi_match across the following fields with these boost weights:

FieldBoostNotes
seo×100SEO metadata — highest priority
title×20Page/article/product title
name×20Used by product categories and series
modelName×20Used by products
excerpt×5Short summary
description×5Long description
content×5Rich text / dynamic zone body content

In addition, two prefix queries are run to support partial model/name lookups (e.g. searching hbmx will match hbmx55):

FieldBoostPurpose
modelName×15Prefix match for product model numbers
name×15Prefix match for category/series names

Fuzzy Matching​

The multi_match query uses fuzziness: "AUTO", which automatically adjusts the allowed edit distance based on term length:

Term lengthMax edits allowed
1–2 chars0 (exact match only)
3–5 chars1
6+ chars2

prefix_length: 2 means the first 2 characters of the query must always match exactly.


Language / Locale Filtering​

When a language parameter is provided (e.g. language=en), results are filtered to match either:

  • Documents with locale equal to the requested language, or
  • Documents with no locale set (null/missing) — this covers content types like api::faq.faq that are not localised.

Result Limits​

  • A maximum of 50 documents are returned per query.
  • The frontend paginates non-product results in pages of 5.
  • Product results are shown in a carousel (all at once) or grouped by series in the Products tab.

Frontend Routing (Search Result URLs)​

Each content type maps to a frontend URL:

Content TypeURL Pattern
api::product.product/products/{categorySlug}/{seriesSlug}/{slug}
api::product-category.product-category/products/{slug}
api::blog-post.blog-post/resources/blog/{slug}
api::news-article.news-article/resources/news/{slug}
api::event.event/resources/events/{slug}
api::testimonial.testimonial/resources/testimonials/{slug}
api::video.video/resources/videos (opens inline player)
api::training.training/resources/trainings (opens inline player)
api::faq.faq/faqs/{categorySlug}?faq={documentId} — opens the FAQ accordion item directly
api::faqs-category.faqs-category/faqs/{slug}
api::content-page.content-page/{slug}
api::contacts-page.contacts-page/contacts