From b0fc5aa42a5552628253a96ea81ff5457b261c21 Mon Sep 17 00:00:00 2001 From: Chris Beer Date: Thu, 1 Aug 2024 10:57:41 -0700 Subject: [PATCH 1/2] Use a special qf for single-term queries --- app/models/search_builder.rb | 12 ++++++++++++ spec/models/search_builder_spec.rb | 17 +++++++++++++++++ 2 files changed, 29 insertions(+) diff --git a/app/models/search_builder.rb b/app/models/search_builder.rb index a4113c7ff..acb130ac3 100644 --- a/app/models/search_builder.rb +++ b/app/models/search_builder.rb @@ -12,6 +12,7 @@ class SearchBuilder < Blacklight::SearchBuilder self.default_processor_chain += [:database_prefix_search] self.default_processor_chain += [:modify_params_for_cjk, :modify_params_for_cjk_advanced] self.default_processor_chain += [:consolidate_home_page_params] + self.default_processor_chain += [:modify_single_term_qf] # Override range limit to only add parameters on search pages, not the home page def add_range_limit_params(*args) @@ -34,6 +35,17 @@ def database_prefix_search(solr_params) solr_params[:fq] << "title_sort:/[#{blacklight_params[:prefix]}].*/" end + # Solr edismax does not apply phrase boosts to single-term matches. When we have a single term query, + # we can use a different set of query boosts to give better results. + def modify_single_term_qf(solr_params) + return unless blacklight_params && blacklight_params[:q].present? && solr_params[:qf].blank? + + q_str = blacklight_params[:q] + return unless q_str.split.size == 1 + + solr_params[:qf] = '${qf_single_term}' + end + private def page_location diff --git a/spec/models/search_builder_spec.rb b/spec/models/search_builder_spec.rb index 4413c3fe3..0823c2d91 100644 --- a/spec/models/search_builder_spec.rb +++ b/spec/models/search_builder_spec.rb @@ -34,6 +34,23 @@ end end + describe 'single term query' do + it "sets the single-term query fields" do + solr_params = search_builder.with(q: 'singleterm').to_hash + expect(solr_params[:qf]).to eq '${qf_single_term}' + end + + it "leaves multi-term queries alone" do + solr_params = search_builder.with(q: 'multi term').to_hash + expect(solr_params[:qf]).to be_nil + end + + it "leaves fielded search queries alone" do + solr_params = search_builder.with(q: 'multi term', search_field: 'search_title').to_hash + expect(solr_params[:qf]).to eq '${qf_title}' + end + end + describe "advanced search" do let(:action_name) { 'advanced_search' } From 6dbb238596b89c8876aa3af05f29ddfc3069675e Mon Sep 17 00:00:00 2001 From: Chris Beer Date: Thu, 1 Aug 2024 11:06:07 -0700 Subject: [PATCH 2/2] Add a feature-flag so we can roll this out easier. --- app/models/search_builder.rb | 1 + config/settings.yml | 3 +++ spec/models/search_builder_spec.rb | 4 ++++ 3 files changed, 8 insertions(+) diff --git a/app/models/search_builder.rb b/app/models/search_builder.rb index acb130ac3..9cd253d71 100644 --- a/app/models/search_builder.rb +++ b/app/models/search_builder.rb @@ -38,6 +38,7 @@ def database_prefix_search(solr_params) # Solr edismax does not apply phrase boosts to single-term matches. When we have a single term query, # we can use a different set of query boosts to give better results. def modify_single_term_qf(solr_params) + return unless Settings.search.use_single_term_query_fields return unless blacklight_params && blacklight_params[:q].present? && solr_params[:qf].blank? q_str = blacklight_params[:q] diff --git a/config/settings.yml b/config/settings.yml index 5e2e09c59..780779c39 100644 --- a/config/settings.yml +++ b/config/settings.yml @@ -98,6 +98,9 @@ dynamic_sitemap_solr_endpoint: 'select' browse_nearby: enabled: true +search: + use_single_term_query_fields: false + libraries: ARS: about_url: https://library.stanford.edu/libraries/archive-recorded-sound diff --git a/spec/models/search_builder_spec.rb b/spec/models/search_builder_spec.rb index 0823c2d91..a91cc85fe 100644 --- a/spec/models/search_builder_spec.rb +++ b/spec/models/search_builder_spec.rb @@ -35,6 +35,10 @@ end describe 'single term query' do + before do + allow(Settings.search).to receive(:use_single_term_query_fields).and_return(true) + end + it "sets the single-term query fields" do solr_params = search_builder.with(q: 'singleterm').to_hash expect(solr_params[:qf]).to eq '${qf_single_term}'