Module: Blacklight::Solr::SearchBuilderBehavior
- Extended by:
- ActiveSupport::Concern
- Included in:
- SearchBuilder
- Defined in:
- lib/blacklight/solr/search_builder_behavior.rb
Instance Method Summary collapse
- #add_additional_filters(solr_parameters, additional_filters = nil) ⇒ Object
-
#add_adv_search_clauses(solr_parameters) ⇒ Object
Transform “clause” parameters into the Solr JSON Query DSL.
-
#add_facet_fq_to_solr(solr_parameters) ⇒ Object
Add any existing facet limits, stored in app-level HTTP query as :f, to solr as appropriate :fq query.
- #add_facet_paging_to_solr(solr_params) ⇒ Object
- #add_facet_suggestion_parameters(solr_params) ⇒ Object
-
#add_facetting_to_solr(solr_parameters) ⇒ Object
Add appropriate Solr facetting directives in, including taking account of our facet paging/‘more’.
-
#add_group_config_to_solr(solr_parameters) ⇒ Object
Remove the group parameter if we’ve faceted on the group field (e.g. for the full results for a group).
-
#add_paging_to_solr(solr_params) ⇒ Object
copy paging params from BL app over to solr, changing app level per_page and page to Solr rows and start.
-
#add_query_to_solr(solr_parameters) ⇒ Object
Take the user-entered query, and put it in the solr params, including config’s “search field” params for current search field.
- #add_search_field_default_parameters(solr_parameters) ⇒ Object
- #add_search_field_with_json_query_parameters(solr_parameters) ⇒ Object
- #add_solr_facet_json_params(solr_parameters, field_name, facet, **additional_parameters) ⇒ Object
- #add_solr_fields_to_query(solr_parameters) ⇒ Object
-
#add_sorting_to_solr(solr_parameters) ⇒ Object
copy sorting params from BL app over to solr.
-
#adv_search_clause(clause, default_op) ⇒ Array
The first element is the query operator and the second is the value to add.
-
#default_solr_parameters(solr_parameters) ⇒ Object
Start with general defaults from BL config.
-
#facet_limit_for(facet_field) ⇒ Object
Look up facet limit for given facet_field.
-
#facet_limit_with_pagination(field_name) ⇒ Object
Support facet paging and ‘more’ links, by sending a facet.limit one more than what we want to page at, according to configured facet limits.
-
#solr_param_quote(val, options = {}) ⇒ Object
A helper method used for generating solr LocalParams, put quotes around the term unless it’s a bare-word.
- #with_ex_local_param(ex, value) ⇒ Object
Instance Method Details
#add_additional_filters(solr_parameters, additional_filters = nil) ⇒ Object
66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 |
# File 'lib/blacklight/solr/search_builder_behavior.rb', line 66 def add_additional_filters(solr_parameters, additional_filters = nil) q = additional_filters || @additional_filters return if q.blank? if q.values.any?(&:blank?) # if any field parameters are empty, exclude _all_ results solr_parameters.append_query "{!lucene}NOT *:*" else composed_query = q.map do |field, values| "#{field}:(#{Array(values).map { |x| solr_param_quote(x) }.join(' OR ')})" end.join(" AND ") solr_parameters.append_query "{!lucene}#{composed_query}" end solr_parameters[:defType] = 'lucene' solr_parameters[:spellcheck] = 'false' end |
#add_adv_search_clauses(solr_parameters) ⇒ Object
Transform “clause” parameters into the Solr JSON Query DSL
96 97 98 99 100 101 102 103 104 105 106 107 108 109 |
# File 'lib/blacklight/solr/search_builder_behavior.rb', line 96 def add_adv_search_clauses(solr_parameters) return if search_state.clause_params.blank? defaults = { must: [], must_not: [], should: [] } default_op = blacklight_params[:op]&.to_sym || :must solr_parameters[:mm] = 1 if default_op == :should && search_state.clause_params.values.any? { |clause| } search_state.clause_params.each_value do |clause| op, query = adv_search_clause(clause, default_op) next unless defaults.key?(op) solr_parameters.append_boolean_query(op, query) end end |
#add_facet_fq_to_solr(solr_parameters) ⇒ Object
Add any existing facet limits, stored in app-level HTTP query as :f, to solr as appropriate :fq query.
124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 |
# File 'lib/blacklight/solr/search_builder_behavior.rb', line 124 def add_facet_fq_to_solr(solr_parameters) # convert a String value into an Array if solr_parameters[:fq].is_a? String solr_parameters[:fq] = [solr_parameters[:fq]] end search_state.filters.each do |filter| if filter.config.filter_query_builder filter_query, subqueries = filter.config.filter_query_builder.call(self, filter, solr_parameters) Array(filter_query).each do |fq| solr_parameters.append_filter_query(fq) end solr_parameters.merge!(subqueries) if subqueries else filter.values.compact_blank.each do |value| filter_query, subqueries = if value.is_a?(Array) facet_inclusive_value_to_fq_string(filter.key, value.compact_blank) else facet_value_to_fq_string(filter.config.key, value) end solr_parameters.append_filter_query filter_query solr_parameters.merge!(subqueries) if subqueries end end end end |
#add_facet_paging_to_solr(solr_params) ⇒ Object
245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 |
# File 'lib/blacklight/solr/search_builder_behavior.rb', line 245 def add_facet_paging_to_solr(solr_params) return if facet.blank? facet_config = blacklight_config.facet_fields[facet] solr_params[:rows] = 0 limit = if solr_params["facet.limit"] solr_params["facet.limit"].to_i else facet_config.fetch(:more_limit, blacklight_config.default_more_limit) end page = search_state.facet_page sort = search_state.facet_sort prefix = search_state.facet_prefix offset = (page - 1) * limit if facet_config.json add_solr_facet_json_params(solr_parameters, facet, facet_config, limit: limit + 1, offset: offset, sort: sort, prefix: prefix) return end # Now override with our specific things for fetching facet values facet_ex = facet_config.respond_to?(:ex) ? facet_config.ex : nil solr_params[:'facet.field'] = with_ex_local_param(facet_ex, facet_config.field) # Need to set as f.facet_field.facet.* to make sure we # override any field-specific default in the solr request handler. solr_params[:"f.#{facet_config.field}.facet.limit"] = limit + 1 solr_params[:"f.#{facet_config.field}.facet.offset"] = offset solr_params[:"f.#{facet_config.field}.facet.sort"] = sort if sort solr_params[:"f.#{facet_config.field}.facet.prefix"] = prefix if prefix end |
#add_facet_suggestion_parameters(solr_params) ⇒ Object
280 281 282 283 284 285 |
# File 'lib/blacklight/solr/search_builder_behavior.rb', line 280 def add_facet_suggestion_parameters(solr_params) return if facet.blank? || facet_suggestion_query.blank? solr_params[:'facet.contains'] = facet_suggestion_query[0..50] solr_params[:'facet.contains.ignoreCase'] = true end |
#add_facetting_to_solr(solr_parameters) ⇒ Object
Add appropriate Solr facetting directives in, including taking account of our facet paging/‘more’. This is not about solr ‘fq’, this is about solr facet.* params.
172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 |
# File 'lib/blacklight/solr/search_builder_behavior.rb', line 172 def add_facetting_to_solr(solr_parameters) facet_fields_to_include_in_request.each do |field_name, facet| solr_parameters[:facet] ||= true if facet.json add_solr_facet_json_params(solr_parameters, field_name, facet) next end if facet.pivot solr_parameters.append_facet_pivot with_ex_local_param(facet.ex, facet.pivot.join(",")) elsif facet.query solr_parameters.append_facet_query facet.query.values.map { |x| with_ex_local_param(facet.ex, x[:fq]) } else solr_parameters.append_facet_fields with_ex_local_param(facet.ex, facet.field) end if facet.sort solr_parameters[:"f.#{facet.field}.facet.sort"] = facet.sort end if facet.solr_params facet.solr_params.each do |k, v| solr_parameters[:"f.#{facet.field}.#{k}"] = v end end limit = facet_limit_with_pagination(field_name) solr_parameters[:"f.#{facet.field}.facet.limit"] = limit if limit end end |
#add_group_config_to_solr(solr_parameters) ⇒ Object
Remove the group parameter if we’ve faceted on the group field (e.g. for the full results for a group)
241 242 243 |
# File 'lib/blacklight/solr/search_builder_behavior.rb', line 241 def add_group_config_to_solr solr_parameters solr_parameters[:group] = false if search_state.filter(grouped_key_for_results).any? end |
#add_paging_to_solr(solr_params) ⇒ Object
copy paging params from BL app over to solr, changing app level per_page and page to Solr rows and start.
226 227 228 229 230 231 232 |
# File 'lib/blacklight/solr/search_builder_behavior.rb', line 226 def add_paging_to_solr(solr_params) rows(solr_params[:rows] || 10) if rows.nil? solr_params[:rows] = rows solr_params[:start] = start if start.nonzero? end |
#add_query_to_solr(solr_parameters) ⇒ Object
Take the user-entered query, and put it in the solr params, including config’s “search field” params for current search field. also include setting spellcheck.q.
49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 |
# File 'lib/blacklight/solr/search_builder_behavior.rb', line 49 def add_query_to_solr(solr_parameters) ## # Create Solr 'q' including the user-entered q, prefixed by any # solr LocalParams in config, using solr LocalParams syntax. # http://wiki.apache.org/solr/LocalParams ## if search_field&.query_builder.present? add_search_field_query_builder_params(solr_parameters) elsif search_field&.clause_params.present? add_search_field_with_json_query_parameters(solr_parameters) elsif search_field&.solr_local_parameters.present? add_search_field_with_local_parameters(solr_parameters) elsif !search_state&.query_param.is_a?(Hash) solr_parameters.append_query search_state.query_param end end |
#add_search_field_default_parameters(solr_parameters) ⇒ Object
34 35 36 37 38 39 40 41 42 43 |
# File 'lib/blacklight/solr/search_builder_behavior.rb', line 34 def add_search_field_default_parameters(solr_parameters) ### # Merge in search field configured values, if present, over-writing general # defaults if search_field solr_parameters[:qt] = search_field.qt if search_field.qt solr_parameters.deep_merge!(search_field.solr_parameters) if search_field.solr_parameters end end |
#add_search_field_with_json_query_parameters(solr_parameters) ⇒ Object
86 87 88 89 90 91 92 93 |
# File 'lib/blacklight/solr/search_builder_behavior.rb', line 86 def add_search_field_with_json_query_parameters(solr_parameters) return unless search_state.query_param bool_query = search_field.clause_params.transform_values { |v| v.merge(query: search_state.query_param) } solr_parameters["spellcheck.q"] ||= search_state.query_param solr_parameters.append_boolean_query(:must, bool_query) end |
#add_solr_facet_json_params(solr_parameters, field_name, facet, **additional_parameters) ⇒ Object
153 154 155 156 157 158 159 160 161 162 163 164 165 166 |
# File 'lib/blacklight/solr/search_builder_behavior.rb', line 153 def add_solr_facet_json_params(solr_parameters, field_name, facet, **additional_parameters) solr_parameters[:json] ||= { facet: {} } solr_parameters[:json][:facet] ||= {} field_config = facet.json.respond_to?(:reverse_merge) ? facet.json : {} field_config = field_config.reverse_merge( type: 'terms', field: facet.field, limit: facet_limit_with_pagination(field_name) ).merge(additional_parameters) solr_parameters[:json][:facet][field_name] = field_config.compact_blank end |
#add_solr_fields_to_query(solr_parameters) ⇒ Object
204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 |
# File 'lib/blacklight/solr/search_builder_behavior.rb', line 204 def add_solr_fields_to_query solr_parameters blacklight_config.show_fields.select(&method(:should_add_field_to_request?)).each_value do |field| field.solr_params.each do |k, v| solr_parameters[:"f.#{field.field}.#{k}"] = v end if field.solr_params end blacklight_config.index_fields.select(&method(:should_add_field_to_request?)).each_value do |field| if field.highlight solr_parameters[:hl] = true solr_parameters.append_highlight_field field.field end field.solr_params.each do |k, v| solr_parameters[:"f.#{field.field}.#{k}"] = v end if field.solr_params end end |
#add_sorting_to_solr(solr_parameters) ⇒ Object
copy sorting params from BL app over to solr
236 237 238 |
# File 'lib/blacklight/solr/search_builder_behavior.rb', line 236 def add_sorting_to_solr(solr_parameters) solr_parameters[:sort] = sort if sort.present? end |
#adv_search_clause(clause, default_op) ⇒ Array
Returns the first element is the query operator and the second is the value to add.
112 113 114 115 116 117 118 119 |
# File 'lib/blacklight/solr/search_builder_behavior.rb', line 112 def adv_search_clause(clause, default_op) op = clause[:op]&.to_sym || default_op field = (blacklight_config.search_fields || {})[clause[:field]] if clause[:field] return unless field&.clause_params && clause[:query].present? [op, field.clause_params.transform_values { |v| v.merge(query: clause[:query]) }] end |
#default_solr_parameters(solr_parameters) ⇒ Object
Start with general defaults from BL config. Need to use custom merge to dup values, to avoid later mutating the original by mistake.
22 23 24 25 26 27 28 29 30 31 32 |
# File 'lib/blacklight/solr/search_builder_behavior.rb', line 22 def default_solr_parameters(solr_parameters) blacklight_config.default_solr_params.each do |key, value| solr_parameters[key] ||= if value.respond_to? :deep_dup value.deep_dup elsif value.respond_to?(:dup) && value.duplicable? value.dup else value end end end |
#facet_limit_for(facet_field) ⇒ Object
Look up facet limit for given facet_field. Will look at config, and if config is ‘true’ will look up from Solr @response if available. If no limit is avaialble, returns nil. Used from #add_facetting_to_solr to supply f.fieldname.facet.limit values in solr request (no @response available), and used in display (with @response available) to create a facet paginator with the right limit.
301 302 303 304 305 306 307 308 |
# File 'lib/blacklight/solr/search_builder_behavior.rb', line 301 def facet_limit_for(facet_field) facet = blacklight_config.facet_fields[facet_field] return if facet.blank? if facet.limit facet.limit == true ? blacklight_config.default_facet_limit : facet.limit end end |
#facet_limit_with_pagination(field_name) ⇒ Object
Support facet paging and ‘more’ links, by sending a facet.limit one more than what we want to page at, according to configured facet limits.
313 314 315 316 317 318 319 320 321 322 323 |
# File 'lib/blacklight/solr/search_builder_behavior.rb', line 313 def facet_limit_with_pagination(field_name) limit = facet_limit_for(field_name) return if limit.nil? if limit > 0 limit + 1 else limit end end |
#solr_param_quote(val, options = {}) ⇒ Object
A helper method used for generating solr LocalParams, put quotes around the term unless it’s a bare-word. Escape internal quotes if needed.
329 330 331 332 333 334 335 336 337 338 339 |
# File 'lib/blacklight/solr/search_builder_behavior.rb', line 329 def solr_param_quote(val, = {}) val = val.to_s [:quote] ||= '"' unless val =~ /^[a-zA-Z0-9$_\-\^]+$/ val = [:quote] + # Yes, we need crazy escaping here, to deal with regexp esc too! val.gsub("'", "\\\\'").gsub('"', "\\\\\"") + [:quote] end val end |
#with_ex_local_param(ex, value) ⇒ Object
287 288 289 290 291 292 293 |
# File 'lib/blacklight/solr/search_builder_behavior.rb', line 287 def with_ex_local_param(ex, value) if ex "{!ex=#{ex}}#{value}" else value end end |