Skip to content

Commit f4d1a1f

Browse files
committed
add meilisearch
this thing is way too fast! only downside is that indexing takes a bit longer, and the search indexes are big (16Gi for 2.7 million records) i have no idea how to properly integrate it in the UI, but it seems promising :^)
1 parent d5c1e66 commit f4d1a1f

File tree

8 files changed

+62
-8
lines changed

8 files changed

+62
-8
lines changed

Gemfile

+1
Original file line numberDiff line numberDiff line change
@@ -119,3 +119,4 @@ gem "mail", "~> 2.7.1"
119119

120120
gem "prometheus-client", "~> 4.2"
121121

122+
gem "meilisearch-rails", "~> 0.10.1"

Gemfile.lock

+5
Original file line numberDiff line numberDiff line change
@@ -249,6 +249,10 @@ GEM
249249
mail (2.7.1)
250250
mini_mime (>= 0.1.1)
251251
marcel (1.0.2)
252+
meilisearch (0.25.1)
253+
httparty (>= 0.17.1, < 0.22.0)
254+
meilisearch-rails (0.10.1)
255+
meilisearch (~> 0.25.0)
252256
method_source (1.0.0)
253257
mime-types (3.5.1)
254258
mime-types-data (~> 3.2015)
@@ -535,6 +539,7 @@ DEPENDENCIES
535539
letter_opener
536540
lograge
537541
mail (~> 2.7.1)
542+
meilisearch-rails (~> 0.10.1)
538543
mini_magick
539544
net-imap
540545
net-pop

Procfile.dev

+1
Original file line numberDiff line numberDiff line change
@@ -2,3 +2,4 @@ web: unset PORT && bin/rails server
22
worker: bundle exec sidekiq
33
css: yarn build:css --watch
44
js: yarn build --watch
5+
search: meilisearch --no-analytics --env development --db-path tmp/meilisearch/db --dump-dir tmp/meilisearch/dump --master-key justfordev42069e621

app/controllers/search_controller.rb

+29-3
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,35 @@
11
class SearchController < ApplicationController
22
def index
33
@results = []
4-
query = params[:q]
5-
return if query.blank?
4+
@query = params[:q]
5+
return if @query.blank?
66

7-
@results = []
7+
@results = if params[:multi_search] == "1"
8+
multi_search_experiment
9+
else
10+
[*Answer.search(@query), *Question.search(@query)]
11+
end
12+
end
13+
14+
private
15+
16+
def multi_search_experiment
17+
MeiliSearch::Rails.client.multi_search(
18+
[Answer, Question].map do |klass|
19+
{
20+
q: @query,
21+
index_uid: klass.name.to_s,
22+
show_ranking_score: true,
23+
}
24+
end
25+
)["results"].flat_map do |h|
26+
model = h["indexUid"].constantize # bad practice!
27+
results = model.find(h["hits"].pluck("id")).map { |r| [r.id.to_s, r] }.to_h
28+
h["hits"].map { |hit| [hit["_rankingScore"], results[hit["id"]]] }
29+
end
30+
.sort_by(&:first)
31+
.reverse
32+
.tap { |results| Rails.logger.debug(results) }
33+
.map(&:last)
834
end
935
end

app/models/answer.rb

+6
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,12 @@
11
class Answer < ApplicationRecord
22
extend Answer::TimelineMethods
33

4+
include MeiliSearch::Rails
5+
6+
meilisearch do
7+
attribute :content
8+
end
9+
410
belongs_to :user, counter_cache: :answered_count
511
belongs_to :question, counter_cache: :answer_count
612
has_many :comments, dependent: :destroy

app/models/question.rb

+6
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,12 @@
11
class Question < ApplicationRecord
22
include Question::AnswerMethods
33

4+
include MeiliSearch::Rails
5+
6+
meilisearch do
7+
attribute :content
8+
end
9+
410
belongs_to :user, optional: true
511
has_many :answers, dependent: :destroy
612
has_many :inboxes, dependent: :destroy

app/views/search/index.haml

+6-5
Original file line numberDiff line numberDiff line change
@@ -3,18 +3,19 @@
33
.col-sm-10.col-md-10.col-lg-9.mx-auto
44
.card
55
.card-body
6-
= bootstrap_form_tag layout: :inline, method: :get do |f|
7-
= f.text_field :q, skip_label: true, append: f.primary("Search")
6+
= bootstrap_form_with url: search_path, layout: :inline, method: :get do |f|
7+
= f.text_field :q, skip_label: true, append: f.primary("Search"), value: params[:q]
8+
= f.check_box :multi_search, label: "Multisearch"
89
- unless @results.blank?
910
.container-lg.container--main
1011
.row
1112
.col-sm-10.col-md-10.col-lg-9.mx-auto
1213
- @results.each do |result|
13-
- case result.searchable
14+
- case result
1415
- when Answer
15-
= render "answerbox", a: result.searchable, display_all: false, subscribed_answer_ids: []
16+
= render "answerbox", a: result, display_all: false, subscribed_answer_ids: []
1617
- when Question
17-
= render "shared/question", q: result.searchable, type: nil
18+
= render "shared/question", q: result, type: nil
1819

1920
= render 'shared/links'
2021

config/initializers/meilisearch.rb

+8
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
# frozen_string_literal: true
2+
3+
return unless ENV["SEARCH_ENABLED"] == "true"
4+
5+
MeiliSearch::Rails.configuration = {
6+
meilisearch_url: ENV.fetch("MEILISEARCH_HOST", "http://localhost:7700"),
7+
meilisearch_api_key: ENV.fetch("MEILISEARCH_API_KEY", "justfordev42069e621")
8+
}

0 commit comments

Comments
 (0)