Avoid duplicated queries and, instead, bump the last ones

This commit is contained in:
Jorge Manrubia
2025-07-03 21:48:25 +02:00
parent 020c99fc99
commit fef9e74503
7 changed files with 55 additions and 6 deletions
+1 -1
View File
@@ -3,6 +3,6 @@ class SearchesController < ApplicationController
def show
@search_results = Current.user.search(@query_terms).limit(50)
@recent_search_queries = Current.user.search_queries.order(created_at: :desc).limit(50).uniq(&:terms)
@recent_search_queries = Current.user.search_queries.order(updated_at: :desc).limit(10)
end
end
+3 -1
View File
@@ -10,6 +10,8 @@ module User::Searcher
end
def remember_search(terms)
search_queries.create(terms: terms) if search_queries.last&.terms != terms
search_queries.find_or_create_by(terms: terms).tap do |search_query|
search_query.touch unless search_query.previously_new_record?
end
end
end
@@ -0,0 +1,5 @@
class AddIndexToSearchQueries < ActiveRecord::Migration[8.1]
def change
add_index :search_queries, %w[ user_id updated_at ], unique: true
end
end
Generated
+2 -1
View File
@@ -10,7 +10,7 @@
#
# It's strongly recommended that you check this file into your version control system.
ActiveRecord::Schema[8.1].define(version: 2025_07_02_211937) do
ActiveRecord::Schema[8.1].define(version: 2025_07_03_193928) do
create_table "accesses", force: :cascade do |t|
t.datetime "accessed_at"
t.integer "collection_id", null: false
@@ -315,6 +315,7 @@ ActiveRecord::Schema[8.1].define(version: 2025_07_02_211937) do
t.datetime "updated_at", null: false
t.integer "user_id", null: false
t.index ["user_id", "terms"], name: "index_search_queries_on_user_id_and_terms"
t.index ["user_id", "updated_at"], name: "index_search_queries_on_user_id_and_updated_at", unique: true
t.index ["user_id"], name: "index_search_queries_on_user_id"
end
+18 -1
View File
@@ -2312,6 +2312,23 @@ indexes:
nulls_not_distinct:
comment:
valid: true
- !ruby/object:ActiveRecord::ConnectionAdapters::IndexDefinition
table: search_queries
name: index_search_queries_on_user_id_and_updated_at
unique: true
columns:
- user_id
- updated_at
lengths: {}
orders: {}
opclasses: {}
where:
type:
using:
include:
nulls_not_distinct:
comment:
valid: true
search_results: []
sessions:
- !ruby/object:ActiveRecord::ConnectionAdapters::IndexDefinition
@@ -2499,4 +2516,4 @@ indexes:
comment:
valid: true
workflows: []
version: 20250702211937
version: 20250703193928
+19
View File
@@ -0,0 +1,19 @@
#!/usr/bin/env ruby
require_relative "../config/environment"
ApplicationRecord.with_each_tenant do |tenant|
User.find_each do |user|
search_queries = Set.new
to_delete = []
user.search_queries.find_each do |search_query|
if search_queries.include?(search_query.terms)
to_delete << search_query
end
search_queries << search_query.terms
end
to_delete.each(&:destroy)
end
end
+7 -2
View File
@@ -13,11 +13,16 @@ class User::SearcherTest < ActiveSupport::TestCase
assert_equal "broken", @user.search_queries.last.terms
end
test "don't duplicate repeated searches" do
@user.remember_search("broken")
test "don't duplicate repeated searches but touch the existing match" do
search_result = @user.remember_search("broken")
original_updated_at = search_result.updated_at
travel_to 1.day.from_now
assert_no_difference -> { @user.search_queries.count }, +1 do
@user.remember_search("broken")
end
assert search_result.reload.updated_at > original_updated_at
end
end