Create a Custom Order for the Autocomplete in Shopify

I have an unusual setup in Shopify. I’ve been able to get almost all the way there with what Algolia provides in the app. However, I need to do one thing that I can’t seem to find a way around.

In the Autocomplete display, I need 4 columns.

Column 1, 7 Products of the Product Type “XX”
Column 2, 7 Products of the Product Type “YY”
Column 3, 7 Products of the Product Type “ZZ”
Column 4, 7 Articles

I can get almost there. Is there a way to sort what shows up in what set? For instance, can I create a sub of <div class="aa-dataset-products"></div> that only shows the products of a specific type?

It seems like this is more straightforward in the instantsearch. I’m having a really hard time seeing how to do this in the Autocomplete.

[Disclaimer : this falls outside of our support scope. But I’d by happy to give you pointers. :slight_smile: ]
This is definitely doable!

My first suggestion would be to make a backup of algolia_autocomplete.css.liquid, and wipe it to selectively add back parts that would match your final result (e.g. how to display a single product), because your layout is going to be way different compared to our default one.

Instead of the one dataset, you could definitely have 3:

<div class="aa-dataset-products"></div>
<!-- becomes -->
<div class="aa-dataset-products-xx"></div>
<div class="aa-dataset-products-yy"></div>
<div class="aa-dataset-products-zz"></div>

Then for the JavaScript part, we’re using a function called autocompleteSection.
Create your own called productAutocompleteSection, that will take as parameter the dataset name (everything after aa-dataset) and the filters you want to apply.

You can take most of the existing logic of autocompleteSection:

  function productAutocompleteSection (dataset, filters) {
    // We know it's products here
    // var params = autocomplete[section];
    var params = autocomplete.products;

    // Should always be true, so feel free to remove
    if (params.enabled !== true) return null;

    // Keep those unless you want to have different renders per product column
    var templates = {
      empty: function displayEmptyResultSet (props) {
        return algolia.render(params.templates.empty, Object.assign({}, props, { translations: algolia.translations }));
      },
      suggestion: function displaySuggestion (hit) {
        return algolia.render(params.templates.hit, Object.assign({ _distinct: params.distinct }, hit, {translations: algolia.translations}));
      }
    };

    // With 3 columns, the footer will likely be too much, you can likely remove it
    if (params.templates.footer) {
      templates.footer = function displayFooter (props, content) {
        if (content.nbHits <= params.hitsPerPage) return null;
        if (!autocomplete.showFooter) return null;

        return algolia.render(params.templates.footer, {
          query: props.query,
          nbHits: content.nbHits,
          translations: algolia.translations,
          helpers: algolia.helpers
        });
      }

    }

    return {
      // name: section,
      name: dataset,
      source: $.fn.autocomplete.sources.hits(params.index, {
        // We add filters here
        filters: filters,
        distinct: !!params.distinct,
        hitsPerPage: params.hitsPerPage,
        highlightPreTag: '<span class="aa-highlight">',
        highlightPostTag: '</span>'
      }),
      displayKey: 'title',
      templates: templates
    }
  };

And now, you should be able to replace autocompleteSection with productAutocompleteSection:

autocompleteSection('products')
// becomes
productAutocompleteSection('products-xx', 'product_type:"xx"' /* or tags:"xx" or vendor: "xx"... */),
productAutocompleteSection('products-xx', 'product_type:"yy"'),
productAutocompleteSection('products-xx', 'product_type:"zz"')

Algolia filters doc : https://www.algolia.com/doc/api-reference/api-parameters/filters/

Have fun implementing this, and let us know how it goes!