dwo
dwo

Reputation: 11

Searchkick reindexing not picking up queued changes

I'm following along with the Queuing section of the README which seems to work fine until I begin a re-index operation. I'm noticing that I don't seem to get new changes that have happened after the re-index is started. For example if I have a model Product:

class Product < ApplicationRecord
  searchkick callbacks: :queue
end
  1. Product.reindex(mode: :async)

    • While the index is still reindexing:
      1. new_product = Product.create
      2. Searchkick::ProcessQueueJob.perform_now(class_name: "Product")
  2. new_product is not included in the new index

What is the best way to handle this so that new_product will be included in the new index?

Upvotes: 1

Views: 385

Answers (2)

lao
lao

Reputation: 1680

What you want is not handled by default or automatically. You would have to manually write that new entry to both indexes in order to make it work like you wish.

In Ruby on Rails, I solved this by adding an extension to module Searchkick, what would override all index jobs from Searchkick, then it would check if a indexation is happening, if it is, it would spawn a new job for the new index to perform later. It would be something similar to this:

module Searchkick
  JOBS_TO_OVERRIDE = [BulkReindexJob, ProcessBatchJob, ProcessQueueJob, ReindexV2Job]
  JOBS_TO_OVERRIDE.each do |job_class|
    job_class.class_eval do
      prepend MyModule.ReindexCheck
    end
end

# inside MyModule.ReindexCheck
module Searchkick
  module ReindexCheck
    def perform(*args, **options)
      # here you can check if the reindex is happening
      # and if it is, you can spawn a duplicated job for the new index.
      super(*args, **options)
    end
  end
end

PS.: I would also add some unit tests for all the jobs that we are overriding so if their signatures ever change we capture that in the tests. ;) Good luck

Upvotes: 0

user22874141
user22874141

Reputation:

You don’t t need to set Product.reindex(mode: :async) when you use callbacks: :queue.

Jobs are added to a queue named searchkick in your sidekiq server You need to configure also redis like:

 config_redis = { host: ENV.fetch('REDIS_HOST', '127.0.0.1'), port: ENV.fetch('REDIS_PORT', 6380) }
 Searchkick.redis = Redis.new(config_redis)

then in your service or where you usually trigger the db modification, after that you can call the reindex.

 Searchkick::ProcessQueueJob.perform_later(class_name: "<your model name>")

Upvotes: 0

Related Questions