<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: fuzzygroup</title>
    <description>The latest articles on DEV Community by fuzzygroup (@fuzzygroup).</description>
    <link>https://dev.to/fuzzygroup</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F68424%2Ff0256870-fc76-4d07-a4f2-a6ae3f41a65e.jpg</url>
      <title>DEV Community: fuzzygroup</title>
      <link>https://dev.to/fuzzygroup</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/fuzzygroup"/>
    <language>en</language>
    <item>
      <title>Using MeiliSearch in a Production Rails Environment</title>
      <dc:creator>fuzzygroup</dc:creator>
      <pubDate>Fri, 17 Jun 2022 15:01:51 +0000</pubDate>
      <link>https://dev.to/fuzzygroup/using-meilisearch-in-a-production-rails-environment-5818</link>
      <guid>https://dev.to/fuzzygroup/using-meilisearch-in-a-production-rails-environment-5818</guid>
      <description>&lt;p&gt;I recently migrated &lt;a href="https://www.jobhound.io"&gt;JobHound&lt;/a&gt; from its original hosting (DigitalOcean with a custom Docker based deployer) to a new environment (also DigitalOcean but now with deploys managed via &lt;a href="https://www.hatchbox.io"&gt;HatchBox&lt;/a&gt;).  In the traditional spirit of all IT migrations where you both get something good and lose something good, I got:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Better Performance&lt;/li&gt;
&lt;li&gt;Working SSL; I have no idea why it stopped on the old box but it did and wasn't fixable&lt;/li&gt;
&lt;li&gt;Much better deployment (NO MORE DOCKER!)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;But I also lost something:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;ElasticSearch or ES&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;I had implemented ES as a Docker component that was a part of my overall and it really did work beautifully -- the simplest installation of ES that I've ever experienced.&lt;/p&gt;

&lt;p&gt;When I found that I couldn't install ES on my Mac without messing about with the memory allocations because certain memory allocation options aren't available on Open Java platform, I started to get concerned.  And then ES just proved to be increasingly byzantine to make work (perhaps this is me).  So I was open to new search technologies and I quick perusal of the &lt;a href="https://gorails.com/episodes"&gt;GoRails screencasts&lt;/a&gt; turned me onto &lt;a href="https://www.meilisearch.com/"&gt;MeiliSearch&lt;/a&gt;, a relatively new Rust based search engine.&lt;/p&gt;

&lt;p&gt;I will admit that I have a certain fondness for things written in Rust.  If you aren't aware, Rust is a language which a focus on preventing programmer errors.  And, in my experience, that tends to produce some really great pieces of software.&lt;/p&gt;

&lt;h2&gt;
  
  
  Getting Started
&lt;/h2&gt;

&lt;p&gt;This is the process I used to get MeiliSearch up and running for JobHound.  In about 2 hours, I went from never having used MeiliSearch to a fully working installation both locally and on production.  In my experience, that kicks the snot out of ElasticSearch.&lt;/p&gt;

&lt;h3&gt;
  
  
  Desired Configuration
&lt;/h3&gt;

&lt;p&gt;I'm working on a pretty standard multi box configuration:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;load balancer&lt;/li&gt;
&lt;li&gt;worker&lt;/li&gt;
&lt;li&gt;web1&lt;/li&gt;
&lt;li&gt;web2&lt;/li&gt;
&lt;li&gt;database&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;My plan was to setup MeiliSearch on the worker box and have that do al the indexing and querying.  This means that my web boxes would need to talk to MeiliSearch on the worker box over MeiliSearch's default port of 7700.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Note 1&lt;/strong&gt;: I'm running all this on Digital Ocean using Ubuntu 18.04 Bionic.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Note 2&lt;/strong&gt;: This is best read alongside the &lt;a href="https://blog.meilisearch.com/how-to-integrate-an-extremely-fast-and-relevant-search-into-your-rails-app-using-meilisearch-and-react/"&gt;official docs&lt;/a&gt;.  And the docs are excellent but there are enough things I noticed doing a full installation into both development and production that I wanted to note them.&lt;/p&gt;

&lt;h3&gt;
  
  
  Local Installation for Development
&lt;/h3&gt;

&lt;p&gt;I installed MeiliSearch via brew:&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;brew install meilisearch
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;To confirm that your installation is working correctly, goto &lt;a href="http://localhost:7700/"&gt;http://localhost:7700/&lt;/a&gt; and you should see a web based UI to verify your indices and perform queries.&lt;/p&gt;

&lt;h3&gt;
  
  
  Server Installation for Production Use
&lt;/h3&gt;

&lt;p&gt;Log into your server and change into the /tmp directory:&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;cd /tmp
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;Run:&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;curl -L https://install.meilisearch.com | sh
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;Now you want to move meilisearch to the /usr/bin directory:&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;sudo mv meilisearch /usr/bin/
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;and change its permissions to root:&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;sudo chown root:root /usr/bin/meilisearch
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;
&lt;h3&gt;
  
  
  Adding an API Key
&lt;/h3&gt;

&lt;p&gt;Generate a random high entry token that you can used for an API key.  Here's one way:&lt;/p&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;cat /dev/urandom | base64 | head -c 24
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;This gave me: &lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;AntypkbH8DITLhaRG8ru0SIP 
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;which we will use in the next step.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Note&lt;/strong&gt;: Not my actual API key.&lt;/p&gt;

&lt;h3&gt;
  
  
  Setting MeiliSearch to Run as a Service
&lt;/h3&gt;

&lt;p&gt;Once you have MeiliSearch installed, you need to create a SystemD service file which can be done like this:&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;    sudo cat &amp;lt;&amp;lt; EOF &amp;gt; /etc/systemd/system/meilisearch.service
    [Unit]
    Description=Meilisearch
    After=systemd-user-sessions.service

    [Service]
    Type=simple
    ExecStart=/usr/bin/meilisearch --http-addr 127.0.0.1:7700 --env production --master-key AntypkbH8DITLhaRG8ru0SIP

    [Install]
    WantedBy=default.target
    EOF
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;&lt;strong&gt;VERY, VERY IMPORTANT&lt;/strong&gt;: If you are using this with a multi box install then you need to specify your machine's IP address above NOT 127.0.0.1.&lt;/p&gt;

&lt;p&gt;Once you have installed the service file then you need to use commands like these:&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;systemctl start meilisearch
systemctl status meilisearch
systemctl stop meilisearch
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;to maintain meilisearch.&lt;/p&gt;

&lt;h3&gt;
  
  
  Locking MeiliSearch Down
&lt;/h3&gt;

&lt;p&gt;There are two aspects to locking down MeiliSearch:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;API Key as mentioned above.  By using the same API key on the server process and on the client machine, only searches with that API key will be executed&lt;/li&gt;
&lt;li&gt;Limiting Access.  Use a firewall to govern access to certain ports and machines&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The ufw firewall is a standard Linux thing at this point.  What you need to do is add firewall rules which:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;allow access from web1&lt;/li&gt;
&lt;li&gt;allow access from web2&lt;/li&gt;
&lt;li&gt;allow access from yourself i.e. worker1's ip address&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;These rules are written as follows:&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;sudo ufw allow from 138.x.y.z to any port 7700
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;&lt;strong&gt;Note&lt;/strong&gt;: This would be a real IP address above where x, y, z and replaced by the correct octets of the address.&lt;/p&gt;

&lt;h3&gt;
  
  
  Sidebar: Belt and Suspenders
&lt;/h3&gt;

&lt;p&gt;Given the number of API key breaches these days, I opted to lock down MeiliSearch using both API keys and a firewall rule.  This was very deliberate on my part as once upon a time, an engineer who worked for me, left an unprotected ElasticSearch instance running on a test server.  After that box was exploited for a $30,000 bandwidth, I swore that I'd try to never do that again.&lt;/p&gt;

&lt;h3&gt;
  
  
  Gemfile
&lt;/h3&gt;

&lt;p&gt;To start, you need to use this line in your Gemfile:&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;gem "meilisearch-rails", github: "meilisearch/meilisearch-rails", branch: "release-v0.5.1"
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;The 0.5.1 gem was never released to &lt;a href="https://rubygems.org/gems/meilisearch/versions"&gt;Ruby Gems&lt;/a&gt; so without the line above, you will get the 0.3 version which does not work.  Yes they say that they have fixed this.  And no they haven't (as of the writing of this blog post; &lt;a href="https://github.com/meilisearch/meilisearch-rails/issues/114"&gt;Github Issue&lt;/a&gt;).&lt;/p&gt;

&lt;p&gt;Once you put that in place, you need the obligatory dance of:&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;bundle install
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;
&lt;h3&gt;
  
  
  Initializers - Just Say No
&lt;/h3&gt;

&lt;p&gt;MeiliSearch has you use an initializer in config/initializers like this:&lt;br&gt;
&lt;/p&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight ruby"&gt;&lt;code&gt;&lt;span class="no"&gt;MeiliSearch&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;configuration&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="ss"&gt;meilisearch_host: &lt;/span&gt;&lt;span class="s1"&gt;'http://127.0.0.1:7700'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="ss"&gt;meilisearch_api_key: &lt;/span&gt;&lt;span class="s1"&gt;''&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;I switched that to blocks of code in production.rb and development.rb:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight ruby"&gt;&lt;code&gt;&lt;span class="no"&gt;MeiliSearch&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="no"&gt;Rails&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;configuration&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="ss"&gt;meilisearch_api_key: &lt;/span&gt;&lt;span class="s1"&gt;'AntypkbH8DITLhaRG8ru0SIP'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="ss"&gt;pagination_backend: :kaminari&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="ss"&gt;timeout: &lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="ss"&gt;max_retries: &lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="ss"&gt;meilisearch_host: &lt;/span&gt;&lt;span class="s1"&gt;'http://165.x.y.z:7700'&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;I skipped the initializers because no matter how I used Rails.env.development?, I couldn't make it work with MeiliSearch; bizarre.&lt;/p&gt;

&lt;h3&gt;
  
  
  Model Code
&lt;/h3&gt;

&lt;p&gt;Here is all the code to add to your model:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight ruby"&gt;&lt;code&gt;  &lt;span class="kp"&gt;include&lt;/span&gt; &lt;span class="no"&gt;MeiliSearch&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="no"&gt;Rails&lt;/span&gt;
  &lt;span class="n"&gt;meilisearch&lt;/span&gt; &lt;span class="k"&gt;do&lt;/span&gt;
    &lt;span class="c1"&gt;# all attributes will be sent to Meilisearch if block is left empty&lt;/span&gt;
    &lt;span class="n"&gt;displayed_attributes&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s1"&gt;'id'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'title'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'description'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'location'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'why_rejected'&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
    &lt;span class="n"&gt;searchable_attributes&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s1"&gt;'company'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'title'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'why_rejected'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'location'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'name'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'domain'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'description'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'created_at'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'user_id'&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
    &lt;span class="n"&gt;filterable_attributes&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s1"&gt;'user_id'&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
    &lt;span class="n"&gt;sortable_attributes&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="ss"&gt;:created_at&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="ss"&gt;:updated_at&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
  &lt;span class="k"&gt;end&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Example Search
&lt;/h3&gt;

&lt;p&gt;Here is an example search command that I used in console:&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Job.search("ruby")
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;which returned all jobs matching the term &lt;strong&gt;ruby&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;You can also use filters to restrict what comes back to only the specified user:&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;@jobs = Job.search("ruby", filter: ["user_id=1"])
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;
&lt;h3&gt;
  
  
  Controller
&lt;/h3&gt;

&lt;p&gt;While the MeiliSearch examples give you a lovely React based UI, I'm a bit more old school.  Here's a simple controller which executes the search:&lt;br&gt;
&lt;/p&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight ruby"&gt;&lt;code&gt;&lt;span class="k"&gt;class&lt;/span&gt; &lt;span class="nc"&gt;SearchController&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;&lt;/span&gt; &lt;span class="no"&gt;ApplicationController&lt;/span&gt;
  &lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;index&lt;/span&gt;
    &lt;span class="vi"&gt;@jobs&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="no"&gt;Job&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;search&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;params&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="ss"&gt;:q&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt; &lt;span class="ss"&gt;filter: &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"user_id=&lt;/span&gt;&lt;span class="si"&gt;#{&lt;/span&gt;&lt;span class="n"&gt;current_user&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;id&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="p"&gt;])&lt;/span&gt;
    &lt;span class="vi"&gt;@notes&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="no"&gt;Note&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;search&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;params&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="ss"&gt;:q&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt; &lt;span class="ss"&gt;filter: &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"user_id=&lt;/span&gt;&lt;span class="si"&gt;#{&lt;/span&gt;&lt;span class="n"&gt;current_user&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;id&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="p"&gt;])&lt;/span&gt;
    &lt;span class="vi"&gt;@cover_letters&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="no"&gt;CoverLetter&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;search&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;params&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="ss"&gt;:q&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt; &lt;span class="ss"&gt;filter: &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"user_id=&lt;/span&gt;&lt;span class="si"&gt;#{&lt;/span&gt;&lt;span class="n"&gt;current_user&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;id&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="p"&gt;])&lt;/span&gt;
    &lt;span class="vi"&gt;@tasks&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="no"&gt;Task&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;search&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;params&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="ss"&gt;:q&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt; &lt;span class="ss"&gt;filter: &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"user_id=&lt;/span&gt;&lt;span class="si"&gt;#{&lt;/span&gt;&lt;span class="n"&gt;current_user&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;id&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="p"&gt;])&lt;/span&gt;
  &lt;span class="k"&gt;end&lt;/span&gt;
&lt;span class="k"&gt;end&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;My controller is searching all the user's indexed objects at once and bringing up a UI which shows all of these to the user.&lt;/p&gt;

&lt;h3&gt;
  
  
  Indexing Rake Task
&lt;/h3&gt;

&lt;p&gt;Whenever you implement a search system, you are going to need to re-index everything.  There's just no way around it.  Here is an example rake task which handles re-indexing:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight ruby"&gt;&lt;code&gt;&lt;span class="n"&gt;namespace&lt;/span&gt; &lt;span class="ss"&gt;:search&lt;/span&gt; &lt;span class="k"&gt;do&lt;/span&gt;
  &lt;span class="c1"&gt;# bundle exec rake search:index_all --trace&lt;/span&gt;
  &lt;span class="n"&gt;task&lt;/span&gt; &lt;span class="ss"&gt;:index_all&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="ss"&gt;:environment&lt;/span&gt; &lt;span class="k"&gt;do&lt;/span&gt;
    &lt;span class="n"&gt;klasses&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="no"&gt;Job&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="no"&gt;Note&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="no"&gt;CoverLetter&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="no"&gt;Task&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
    &lt;span class="n"&gt;klasses&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;each&lt;/span&gt; &lt;span class="k"&gt;do&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt;&lt;span class="n"&gt;klass&lt;/span&gt;&lt;span class="o"&gt;|&lt;/span&gt;
      &lt;span class="n"&gt;klass&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;reindex!&lt;/span&gt;
    &lt;span class="k"&gt;end&lt;/span&gt;
  &lt;span class="k"&gt;end&lt;/span&gt;
&lt;span class="k"&gt;end&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Conclusion
&lt;/h2&gt;

&lt;p&gt;I'm now happier with MeiliSearch than I ever was with ElasticSearch.  It was not only simpler and easier to use but I feel I have a better grasp on how MeiliSearch works than I ever have with ElasticSearch.  &lt;/p&gt;

&lt;p&gt;Kudos to the team!  Well done!&lt;/p&gt;

&lt;h2&gt;
  
  
  References
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;a href="https://gorails.com/episodes/how-to-use-meilisearch-rails?autoplay=1"&gt;MeiliSearch screencast&lt;/a&gt; on GoRails&lt;/li&gt;
&lt;li&gt;&lt;a href="https://blog.meilisearch.com/how-to-integrate-an-extremely-fast-and-relevant-search-into-your-rails-app-using-meilisearch-and-react/"&gt;Official Rails Tutorial&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.meilisearch.com/"&gt;MeiliSearch Home Page&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/gorails-screencasts/meilisearch-rails-example/"&gt;Example Rails MeiliSearch App Source code from GoRails&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/meilisearch/meilisearch-rails"&gt;Ruby Gem&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://docs.meilisearch.com/learn/cookbooks/running_production.html#step-2-run-meilisearch-as-a-service"&gt;MeiliSearch in Production&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://docs.meilisearch.com/reference/api/filterable_attributes.html"&gt;Understanding Filterable Attributes&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://docs.meilisearch.com/learn/security/master_api_keys.html"&gt;Master API Keys&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>rails</category>
      <category>meilisearch</category>
      <category>search</category>
    </item>
  </channel>
</rss>
