elasticsearch_helper.rb
3.3 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
module ElasticsearchHelper
def searchable_types
{
:all => { label: _("All Results")},
:text_article => { label: _("Articles")},
:uploaded_file => { label: _("Files")},
:community => { label: _("Communities")},
:event => { label: _("Events")},
:person => { label: _("People")}
}
end
def sort_types
sorts = {
:relevance => { label: _("Relevance")},
:lexical => { label: _("Alphabetical")},
:more_recent => { label: _("More Recent")},
}
selected_type = params[:selected_type] || nil
if selected_type and selected_type.to_sym != :all
klass = selected_type.to_s.classify.constantize
sorts.update klass.especific_sort if klass.respond_to? :especific_sort
end
sorts
end
def process_results
selected_type = (params[:selected_type].presence|| :all).to_sym
selected_type == :all ? search_from_all_models : search_from_model(selected_type)
end
private
def search_from_all_models
begin
filter = (params[:filter] || "" ).to_sym
query = get_query params[:query], sort_by: get_sort_by(filter)
Elasticsearch::Model.search(query,searchable_models, size: default_per_page(params[:per_page])).page(params[:page]).records
rescue
[]
end
end
def search_from_model model
begin
klass = model.to_s.classify.constantize
filter = (params[:filter] || "" ).to_sym
query = get_query params[:query], klass: klass, sort_by: get_sort_by(filter,klass)
klass.search(query, size: default_per_page(params[:per_page])).page(params[:page]).records
rescue
[]
end
end
def default_per_page per_page=nil
per_page ||= 10
end
def get_sort_by sort_by, klass=nil
case sort_by
when :lexical
{ "name.raw" => {"order" => "asc" }}
when :more_recent
{ "created_at" => {"order" => "desc"}}
else
( klass and klass.respond_to?(:get_sort_by) ) ? klass.get_sort_by(sort_by) : nil
end
end
def searchable_models
searchable_types.except(:all).keys.map { | model | model.to_s.classify.constantize }
end
def query_string expression="", models=[]
return { match_all: {} } if not expression
{
query_string: {
query: "*"+expression.downcase.split.join('* *')+"*",
fields: fields_from_models(models),
tie_breaker: 0.4,
minimum_should_match: "100%"
}
}
end
def query_method expression="", models=[]
{
query: {
filtered: {
query: query_string(expression,models),
filter: {
bool: {
should: models.map {|model| model.filter(environment: @environment.id) }
}
}
}
}
}
end
def get_query text="", options={}
klass = options[:klass]
sort_by = options[:sort_by]
models = (klass.nil?) ? searchable_models : [klass]
query = query_method(text, models)
query[:sort] = sort_by if sort_by
query
end
def fields_from_models klasses
fields = Set.new
klasses.each do |klass|
klass::SEARCHABLE_FIELDS.map do |key, value|
if value and value[:weight]
fields.add "#{key}^#{value[:weight]}"
else
fields.add "#{key}"
end
end
end
fields.to_a
end
end