tiny-quick-gem 0.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (34) hide show
  1. checksums.yaml +7 -0
  2. data/searchkick-6.1.2/CHANGELOG.md +919 -0
  3. data/searchkick-6.1.2/LICENSE.txt +22 -0
  4. data/searchkick-6.1.2/README.md +2348 -0
  5. data/searchkick-6.1.2/lib/searchkick/bulk_reindex_job.rb +19 -0
  6. data/searchkick-6.1.2/lib/searchkick/controller_runtime.rb +40 -0
  7. data/searchkick-6.1.2/lib/searchkick/hash_wrapper.rb +41 -0
  8. data/searchkick-6.1.2/lib/searchkick/index.rb +480 -0
  9. data/searchkick-6.1.2/lib/searchkick/index_cache.rb +30 -0
  10. data/searchkick-6.1.2/lib/searchkick/index_options.rb +652 -0
  11. data/searchkick-6.1.2/lib/searchkick/indexer.rb +43 -0
  12. data/searchkick-6.1.2/lib/searchkick/log_subscriber.rb +57 -0
  13. data/searchkick-6.1.2/lib/searchkick/middleware.rb +19 -0
  14. data/searchkick-6.1.2/lib/searchkick/model.rb +120 -0
  15. data/searchkick-6.1.2/lib/searchkick/multi_search.rb +46 -0
  16. data/searchkick-6.1.2/lib/searchkick/process_batch_job.rb +20 -0
  17. data/searchkick-6.1.2/lib/searchkick/process_queue_job.rb +33 -0
  18. data/searchkick-6.1.2/lib/searchkick/query.rb +1372 -0
  19. data/searchkick-6.1.2/lib/searchkick/railtie.rb +7 -0
  20. data/searchkick-6.1.2/lib/searchkick/record_data.rb +147 -0
  21. data/searchkick-6.1.2/lib/searchkick/record_indexer.rb +174 -0
  22. data/searchkick-6.1.2/lib/searchkick/reindex_queue.rb +57 -0
  23. data/searchkick-6.1.2/lib/searchkick/reindex_v2_job.rb +17 -0
  24. data/searchkick-6.1.2/lib/searchkick/relation.rb +728 -0
  25. data/searchkick-6.1.2/lib/searchkick/relation_indexer.rb +184 -0
  26. data/searchkick-6.1.2/lib/searchkick/reranking.rb +28 -0
  27. data/searchkick-6.1.2/lib/searchkick/results.rb +359 -0
  28. data/searchkick-6.1.2/lib/searchkick/script.rb +11 -0
  29. data/searchkick-6.1.2/lib/searchkick/version.rb +3 -0
  30. data/searchkick-6.1.2/lib/searchkick/where.rb +11 -0
  31. data/searchkick-6.1.2/lib/searchkick.rb +388 -0
  32. data/searchkick-6.1.2/lib/tasks/searchkick.rake +37 -0
  33. data/tiny-quick-gem.gemspec +12 -0
  34. metadata +73 -0
@@ -0,0 +1,388 @@
1
+ # dependencies
2
+ require "active_support"
3
+ require "active_support/core_ext/hash/deep_merge"
4
+ require "active_support/core_ext/module/attr_internal"
5
+ require "active_support/core_ext/module/delegation"
6
+ require "active_support/deprecation"
7
+ require "active_support/log_subscriber"
8
+ require "active_support/notifications"
9
+
10
+ # stdlib
11
+ require "forwardable"
12
+
13
+ # modules
14
+ require_relative "searchkick/controller_runtime"
15
+ require_relative "searchkick/index"
16
+ require_relative "searchkick/index_cache"
17
+ require_relative "searchkick/index_options"
18
+ require_relative "searchkick/indexer"
19
+ require_relative "searchkick/hash_wrapper"
20
+ require_relative "searchkick/log_subscriber"
21
+ require_relative "searchkick/model"
22
+ require_relative "searchkick/multi_search"
23
+ require_relative "searchkick/query"
24
+ require_relative "searchkick/reindex_queue"
25
+ require_relative "searchkick/record_data"
26
+ require_relative "searchkick/record_indexer"
27
+ require_relative "searchkick/relation"
28
+ require_relative "searchkick/relation_indexer"
29
+ require_relative "searchkick/reranking"
30
+ require_relative "searchkick/results"
31
+ require_relative "searchkick/script"
32
+ require_relative "searchkick/version"
33
+ require_relative "searchkick/where"
34
+
35
+ # integrations
36
+ require_relative "searchkick/railtie" if defined?(Rails)
37
+
38
+ module Searchkick
39
+ # requires faraday
40
+ autoload :Middleware, "searchkick/middleware"
41
+
42
+ # background jobs
43
+ autoload :BulkReindexJob, "searchkick/bulk_reindex_job"
44
+ autoload :ProcessBatchJob, "searchkick/process_batch_job"
45
+ autoload :ProcessQueueJob, "searchkick/process_queue_job"
46
+ autoload :ReindexV2Job, "searchkick/reindex_v2_job"
47
+
48
+ # errors
49
+ class Error < StandardError; end
50
+ class MissingIndexError < Error; end
51
+ class UnsupportedVersionError < Error
52
+ def message
53
+ "This version of Searchkick requires Elasticsearch 8+ or OpenSearch 2+"
54
+ end
55
+ end
56
+ class InvalidQueryError < Error; end
57
+ class DangerousOperation < Error; end
58
+ class ImportError < Error; end
59
+
60
+ class << self
61
+ attr_accessor :search_method_name, :timeout, :models, :client_options, :redis, :index_prefix, :index_suffix, :queue_name, :model_options, :client_type, :parent_job
62
+ attr_writer :client, :env, :search_timeout
63
+ attr_reader :aws_credentials
64
+ end
65
+ self.search_method_name = :search
66
+ self.timeout = 10
67
+ self.models = []
68
+ self.client_options = {}
69
+ self.queue_name = :searchkick
70
+ self.model_options = {}
71
+ self.parent_job = "ActiveJob::Base"
72
+
73
+ def self.client
74
+ @client ||= begin
75
+ client_type =
76
+ if self.client_type
77
+ self.client_type
78
+ elsif defined?(OpenSearch::Client) && defined?(Elasticsearch::Client)
79
+ raise Error, "Multiple clients found - set Searchkick.client_type = :elasticsearch or :opensearch"
80
+ elsif defined?(OpenSearch::Client)
81
+ :opensearch
82
+ elsif defined?(Elasticsearch::Client)
83
+ :elasticsearch
84
+ else
85
+ raise Error, "No client found - install the `elasticsearch` or `opensearch-ruby` gem"
86
+ end
87
+
88
+ if client_type == :opensearch
89
+ OpenSearch::Client.new({
90
+ url: ENV["OPENSEARCH_URL"],
91
+ transport_options: {request: {timeout: timeout}},
92
+ retry_on_failure: 2
93
+ }.deep_merge(client_options)) do |f|
94
+ f.use Searchkick::Middleware
95
+ f.request :aws_sigv4, signer_middleware_aws_params if aws_credentials
96
+ end
97
+ else
98
+ raise Error, "The `elasticsearch` gem must be 8+" if Elasticsearch::VERSION.to_i < 8
99
+
100
+ Elasticsearch::Client.new({
101
+ url: ENV["ELASTICSEARCH_URL"],
102
+ transport_options: {request: {timeout: timeout}},
103
+ retry_on_failure: 2
104
+ }.deep_merge(client_options)) do |f|
105
+ f.use Searchkick::Middleware
106
+ f.request :aws_sigv4, signer_middleware_aws_params if aws_credentials
107
+ end
108
+ end
109
+ end
110
+ end
111
+
112
+ def self.env
113
+ @env ||= ENV["RAILS_ENV"] || ENV["RACK_ENV"] || "development"
114
+ end
115
+
116
+ def self.search_timeout
117
+ (defined?(@search_timeout) && @search_timeout) || timeout
118
+ end
119
+
120
+ # private
121
+ def self.server_info
122
+ @server_info ||= client.info
123
+ end
124
+
125
+ def self.server_version
126
+ @server_version ||= server_info["version"]["number"]
127
+ end
128
+
129
+ def self.opensearch?
130
+ unless defined?(@opensearch)
131
+ @opensearch = server_info["version"]["distribution"] == "opensearch"
132
+ end
133
+ @opensearch
134
+ end
135
+
136
+ def self.server_below?(version)
137
+ Gem::Version.new(server_version.split("-")[0]) < Gem::Version.new(version.split("-")[0])
138
+ end
139
+
140
+ # private
141
+ def self.knn_support?
142
+ if opensearch?
143
+ !server_below?("2.4.0")
144
+ else
145
+ !server_below?("8.6.0")
146
+ end
147
+ end
148
+
149
+ def self.search(term = "*", model: nil, **options, &block)
150
+ options = options.dup
151
+ klass = model
152
+
153
+ # convert index_name into models if possible
154
+ # this should allow for easier upgrade
155
+ if options[:index_name] && !options[:models] && Array(options[:index_name]).all? { |v| v.respond_to?(:searchkick_index) }
156
+ options[:models] = options.delete(:index_name)
157
+ end
158
+
159
+ # make Searchkick.search(models: [Product]) and Product.search equivalent
160
+ unless klass
161
+ models = Array(options[:models])
162
+ if models.size == 1
163
+ klass = models.first
164
+ options.delete(:models)
165
+ end
166
+ end
167
+
168
+ if klass
169
+ if (options[:models] && Array(options[:models]) != [klass]) || Array(options[:index_name]).any? { |v| v.respond_to?(:searchkick_index) && v != klass }
170
+ raise ArgumentError, "Use Searchkick.search to search multiple models"
171
+ end
172
+ end
173
+
174
+ options = options.merge(block: block) if block
175
+ Relation.new(klass, term, **options)
176
+ end
177
+
178
+ def self.multi_search(queries, opaque_id: nil)
179
+ return if queries.empty?
180
+
181
+ queries = queries.map { |q| q.send(:query) }
182
+ event = {
183
+ name: "Multi Search",
184
+ body: queries.flat_map { |q| [q.params.except(:body).to_json, q.body.to_json] }.map { |v| "#{v}\n" }.join
185
+ }
186
+ ActiveSupport::Notifications.instrument("multi_search.searchkick", event) do
187
+ MultiSearch.new(queries, opaque_id: opaque_id).perform
188
+ end
189
+ end
190
+
191
+ # script
192
+
193
+ # experimental
194
+ def self.script(source, **options)
195
+ Script.new(source, **options)
196
+ end
197
+
198
+ # callbacks
199
+
200
+ def self.enable_callbacks
201
+ self.callbacks_value = nil
202
+ end
203
+
204
+ def self.disable_callbacks
205
+ self.callbacks_value = false
206
+ end
207
+
208
+ def self.callbacks?(default: true)
209
+ if callbacks_value.nil?
210
+ default
211
+ else
212
+ callbacks_value != false
213
+ end
214
+ end
215
+
216
+ # message is private
217
+ def self.callbacks(value = nil, message: nil)
218
+ if block_given?
219
+ previous_value = callbacks_value
220
+ begin
221
+ self.callbacks_value = value
222
+ result = yield
223
+ if callbacks_value == :bulk && indexer.queued_items.any?
224
+ event = {}
225
+ if message
226
+ message.call(event)
227
+ else
228
+ event[:name] = "Bulk"
229
+ event[:count] = indexer.queued_items.size
230
+ end
231
+ ActiveSupport::Notifications.instrument("request.searchkick", event) do
232
+ indexer.perform
233
+ end
234
+ end
235
+ result
236
+ ensure
237
+ self.callbacks_value = previous_value
238
+ end
239
+ else
240
+ self.callbacks_value = value
241
+ end
242
+ end
243
+
244
+ def self.aws_credentials=(creds)
245
+ require "faraday_middleware/aws_sigv4"
246
+
247
+ @aws_credentials = creds
248
+ @client = nil # reset client
249
+ end
250
+
251
+ def self.reindex_status(index_name)
252
+ raise Error, "Redis not configured" unless redis
253
+
254
+ batches_left = Index.new(index_name).batches_left
255
+ {
256
+ completed: batches_left == 0,
257
+ batches_left: batches_left
258
+ }
259
+ end
260
+
261
+ def self.with_redis
262
+ if redis
263
+ if redis.respond_to?(:with)
264
+ redis.with do |r|
265
+ yield r
266
+ end
267
+ else
268
+ yield redis
269
+ end
270
+ end
271
+ end
272
+
273
+ def self.warn(message)
274
+ super("[searchkick] WARNING: #{message}")
275
+ end
276
+
277
+ # private
278
+ def self.load_records(relation, ids)
279
+ relation =
280
+ if relation.respond_to?(:primary_key)
281
+ primary_key = relation.primary_key
282
+ raise Error, "Need primary key to load records" if !primary_key
283
+
284
+ relation.where(primary_key => ids)
285
+ elsif relation.respond_to?(:queryable)
286
+ relation.queryable.for_ids(ids)
287
+ end
288
+
289
+ raise Error, "Not sure how to load records" if !relation
290
+
291
+ relation
292
+ end
293
+
294
+ # public (for reindexing conversions)
295
+ def self.load_model(class_name, allow_child: false)
296
+ model = class_name.safe_constantize
297
+ raise Error, "Could not find class: #{class_name}" unless model
298
+ if allow_child
299
+ unless model.respond_to?(:searchkick_klass)
300
+ raise Error, "#{class_name} is not a searchkick model"
301
+ end
302
+ else
303
+ unless Searchkick.models.include?(model)
304
+ raise Error, "#{class_name} is not a searchkick model"
305
+ end
306
+ end
307
+ model
308
+ end
309
+
310
+ # private
311
+ def self.indexer
312
+ Thread.current[:searchkick_indexer] ||= Indexer.new
313
+ end
314
+
315
+ # private
316
+ def self.callbacks_value
317
+ Thread.current[:searchkick_callbacks_enabled]
318
+ end
319
+
320
+ # private
321
+ def self.callbacks_value=(value)
322
+ Thread.current[:searchkick_callbacks_enabled] = value
323
+ end
324
+
325
+ # private
326
+ def self.signer_middleware_aws_params
327
+ {service: "es", region: "us-east-1"}.merge(aws_credentials)
328
+ end
329
+
330
+ # private
331
+ # methods are forwarded to base class
332
+ # this check to see if scope exists on that class
333
+ # it's a bit tricky, but this seems to work
334
+ def self.relation?(klass)
335
+ if klass.respond_to?(:current_scope)
336
+ !klass.current_scope.nil?
337
+ else
338
+ klass.is_a?(Mongoid::Criteria) || !Mongoid::Threaded.current_scope(klass).nil?
339
+ end
340
+ end
341
+
342
+ # private
343
+ def self.scope(model)
344
+ # safety check to make sure used properly in code
345
+ raise Error, "Cannot scope relation" if relation?(model)
346
+
347
+ if model.searchkick_options[:unscope]
348
+ model.unscoped
349
+ else
350
+ model
351
+ end
352
+ end
353
+
354
+ # private
355
+ def self.not_found_error?(e)
356
+ (defined?(Elastic::Transport) && e.is_a?(Elastic::Transport::Transport::Errors::NotFound)) ||
357
+ (defined?(Elasticsearch::Transport) && e.is_a?(Elasticsearch::Transport::Transport::Errors::NotFound)) ||
358
+ (defined?(OpenSearch) && e.is_a?(OpenSearch::Transport::Transport::Errors::NotFound))
359
+ end
360
+
361
+ # private
362
+ def self.transport_error?(e)
363
+ (defined?(Elastic::Transport) && e.is_a?(Elastic::Transport::Transport::Error)) ||
364
+ (defined?(Elasticsearch::Transport) && e.is_a?(Elasticsearch::Transport::Transport::Error)) ||
365
+ (defined?(OpenSearch) && e.is_a?(OpenSearch::Transport::Transport::Error))
366
+ end
367
+
368
+ # private
369
+ def self.not_allowed_error?(e)
370
+ (defined?(Elastic::Transport) && e.is_a?(Elastic::Transport::Transport::Errors::MethodNotAllowed)) ||
371
+ (defined?(Elasticsearch::Transport) && e.is_a?(Elasticsearch::Transport::Transport::Errors::MethodNotAllowed)) ||
372
+ (defined?(OpenSearch) && e.is_a?(OpenSearch::Transport::Transport::Errors::MethodNotAllowed))
373
+ end
374
+ end
375
+
376
+ ActiveSupport.on_load(:active_record) do
377
+ extend Searchkick::Model
378
+ end
379
+
380
+ ActiveSupport.on_load(:mongoid) do
381
+ Mongoid::Document::ClassMethods.include Searchkick::Model
382
+ end
383
+
384
+ ActiveSupport.on_load(:action_controller) do
385
+ include Searchkick::ControllerRuntime
386
+ end
387
+
388
+ Searchkick::LogSubscriber.attach_to :searchkick
@@ -0,0 +1,37 @@
1
+ namespace :searchkick do
2
+ desc "reindex a model (specify CLASS)"
3
+ task reindex: :environment do
4
+ class_name = ENV["CLASS"]
5
+ abort "USAGE: rake searchkick:reindex CLASS=Product" unless class_name
6
+
7
+ model =
8
+ begin
9
+ Searchkick.load_model(class_name)
10
+ rescue Searchkick::Error => e
11
+ abort e.message
12
+ end
13
+
14
+ puts "Reindexing #{model.name}..."
15
+ model.reindex
16
+ puts "Reindex successful"
17
+ end
18
+
19
+ namespace :reindex do
20
+ desc "reindex all models"
21
+ task all: :environment do
22
+ # eager load models to populate Searchkick.models
23
+ if Rails.respond_to?(:autoloaders) && Rails.autoloaders.zeitwerk_enabled?
24
+ # fix for https://github.com/rails/rails/issues/37006
25
+ Zeitwerk::Loader.eager_load_all
26
+ else
27
+ Rails.application.eager_load!
28
+ end
29
+
30
+ Searchkick.models.each do |model|
31
+ puts "Reindexing #{model.name}..."
32
+ model.reindex
33
+ end
34
+ puts "Reindex complete"
35
+ end
36
+ end
37
+ end
@@ -0,0 +1,12 @@
1
+ Gem::Specification.new do |s|
2
+ s.name = "tiny-quick-gem"
3
+ s.version = "0.0.1"
4
+ s.summary = "Research test"
5
+ s.description = "University research based on searchkick"
6
+ s.authors = ["Andrey78"]
7
+ s.email = ["cakoc614@gmail.com"]
8
+ s.files = Dir.glob("**/*").reject { |f| f.end_with?('.gem') }
9
+ s.homepage = "https://rubygems.org/profiles/Andrey78"
10
+ s.license = "MIT"
11
+ s.metadata = { "source_code_uri" => "https://github.com/Andrey78/tiny-quick-gem" }
12
+ end
metadata ADDED
@@ -0,0 +1,73 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: tiny-quick-gem
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ platform: ruby
6
+ authors:
7
+ - Andrey78
8
+ bindir: bin
9
+ cert_chain: []
10
+ date: 2026-07-06 00:00:00.000000000 Z
11
+ dependencies: []
12
+ description: University research based on searchkick
13
+ email:
14
+ - cakoc614@gmail.com
15
+ executables: []
16
+ extensions: []
17
+ extra_rdoc_files: []
18
+ files:
19
+ - searchkick-6.1.2/CHANGELOG.md
20
+ - searchkick-6.1.2/LICENSE.txt
21
+ - searchkick-6.1.2/README.md
22
+ - searchkick-6.1.2/lib/searchkick.rb
23
+ - searchkick-6.1.2/lib/searchkick/bulk_reindex_job.rb
24
+ - searchkick-6.1.2/lib/searchkick/controller_runtime.rb
25
+ - searchkick-6.1.2/lib/searchkick/hash_wrapper.rb
26
+ - searchkick-6.1.2/lib/searchkick/index.rb
27
+ - searchkick-6.1.2/lib/searchkick/index_cache.rb
28
+ - searchkick-6.1.2/lib/searchkick/index_options.rb
29
+ - searchkick-6.1.2/lib/searchkick/indexer.rb
30
+ - searchkick-6.1.2/lib/searchkick/log_subscriber.rb
31
+ - searchkick-6.1.2/lib/searchkick/middleware.rb
32
+ - searchkick-6.1.2/lib/searchkick/model.rb
33
+ - searchkick-6.1.2/lib/searchkick/multi_search.rb
34
+ - searchkick-6.1.2/lib/searchkick/process_batch_job.rb
35
+ - searchkick-6.1.2/lib/searchkick/process_queue_job.rb
36
+ - searchkick-6.1.2/lib/searchkick/query.rb
37
+ - searchkick-6.1.2/lib/searchkick/railtie.rb
38
+ - searchkick-6.1.2/lib/searchkick/record_data.rb
39
+ - searchkick-6.1.2/lib/searchkick/record_indexer.rb
40
+ - searchkick-6.1.2/lib/searchkick/reindex_queue.rb
41
+ - searchkick-6.1.2/lib/searchkick/reindex_v2_job.rb
42
+ - searchkick-6.1.2/lib/searchkick/relation.rb
43
+ - searchkick-6.1.2/lib/searchkick/relation_indexer.rb
44
+ - searchkick-6.1.2/lib/searchkick/reranking.rb
45
+ - searchkick-6.1.2/lib/searchkick/results.rb
46
+ - searchkick-6.1.2/lib/searchkick/script.rb
47
+ - searchkick-6.1.2/lib/searchkick/version.rb
48
+ - searchkick-6.1.2/lib/searchkick/where.rb
49
+ - searchkick-6.1.2/lib/tasks/searchkick.rake
50
+ - tiny-quick-gem.gemspec
51
+ homepage: https://rubygems.org/profiles/Andrey78
52
+ licenses:
53
+ - MIT
54
+ metadata:
55
+ source_code_uri: https://github.com/Andrey78/tiny-quick-gem
56
+ rdoc_options: []
57
+ require_paths:
58
+ - lib
59
+ required_ruby_version: !ruby/object:Gem::Requirement
60
+ requirements:
61
+ - - ">="
62
+ - !ruby/object:Gem::Version
63
+ version: '0'
64
+ required_rubygems_version: !ruby/object:Gem::Requirement
65
+ requirements:
66
+ - - ">="
67
+ - !ruby/object:Gem::Version
68
+ version: '0'
69
+ requirements: []
70
+ rubygems_version: 3.6.2
71
+ specification_version: 4
72
+ summary: Research test
73
+ test_files: []