diff --git a/src/layouts/search.hbs b/src/layouts/search.hbs index 44a6801d..34206647 100644 --- a/src/layouts/search.hbs +++ b/src/layouts/search.hbs @@ -62,17 +62,25 @@ const searchClient = { ...baseClient, search(requests) { - if (exactMatch) { - requests = requests.map((request) => { - const params = { ...(request.params || {}) }; - if (params.query) { - params.typoTolerance = false; - params.removeWordsIfNoResults = 'none'; - params.optionalWords = []; - } - return { ...request, params }; - }); - } + requests = requests.map((request) => { + const params = { ...(request.params || {}) }; + // Keep empty "root" queries out of Algolia Search analytics. These + // fire on initial page load and during facet-only browsing (no term + // typed). They still return results, but `analytics: false` stops + // them being recorded as a searched term — otherwise they show up as + // "" and dominate the report and skew average CTR. + if (!params.query) { + params.analytics = false; + } + // Exact match: require every term, exact spelling, no optional-word + // fallback. Only meaningful when there's an actual query. + if (exactMatch && params.query) { + params.typoTolerance = false; + params.removeWordsIfNoResults = 'none'; + params.optionalWords = []; + } + return { ...request, params }; + }); return baseClient.search(requests); }, }; @@ -81,6 +89,12 @@ const search = instantsearch({ searchClient, indexName, + // Enable click/conversion analytics. Reuses the global `aa` + // (search-insights) already initialised in algolia-script.hbs, sets + // clickAnalytics on queries, and attaches a queryID so the click + // events we send below are attributed to the search that produced them. + // https://www.algolia.com/doc/api-reference/widgets/insights/js/ + insights: true, routing: { stateMapping: { // Convert UI state to URL parameters @@ -137,18 +151,23 @@ instantsearch.widgets.hits({ container: '.results', templates: { - item: (hit, { html, components }) => { + item: (hit, { html, components, sendEvent }) => { + // Record a click event attributed to the current query (queryID) + // so Algolia can report CTR/CVR for the results page. Uses + // navigator.sendBeacon under the hood, so it survives the + // navigation triggered by the link. + const onHitClick = () => sendEvent('click', hit, 'Hit Clicked'); const isExternal = hit.objectID.startsWith('https'); if (isExternal) { return html`

- + ${components.Highlight({ attribute: 'title', hit })}

- + ${components.Snippet({ attribute: 'intro', hit })}

@@ -164,10 +183,10 @@ return html`