no_fly_list 0.6.0 → 0.7.2

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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 5f1516f63b4ece62151501ea60f15ae1d5c2c3ea5738f22881ad5e2456a74b68
4
- data.tar.gz: c9b88ce48a93a03fd21ade6eccfb0210e788c26ea78150ce92ee5ecf5f0ce8b0
3
+ metadata.gz: 9fb7865780acd9586b0ff700686a1546a4c294f9fc3d7a71fe47f2fb7a6def0c
4
+ data.tar.gz: be5186e8116c5db42c4aa4e3536ab4343b95967f5cd05dcfb64c8f99ebb85270
5
5
  SHA512:
6
- metadata.gz: ea013a28e4c1246f511ae736951a89a2c292668a6d3ce1ecbf2ada940cee52576144f5de4cfebd2f10a38feb3a80f94082cc1d6ab340d692fe14f75e329b0913
7
- data.tar.gz: 9b714d9919bcf14c9fda34bada054f49af0202ab1189f0e487f38d1140df4f27e5580ef3b737adf0a59efc55e19bf381f74cdf2ccdeeb2fcf73d3a49b8135049
6
+ metadata.gz: 630d2aa00cc4b2465321d1040697cff6c54124247275a0b75677d70653fe347ec1c0ad7e9c573dea060de07be1de02977f1ff6f467bfe1465299a1f764e35325
7
+ data.tar.gz: 1201844673a3893a3c760ab1fc88ed6826839d799bca6a93b17c2c3e802fa4e9df4d485bdc5511cec4c7cbf2bdcc3cba9cfd1280970d58b5eaa93492f7ece67a
@@ -39,14 +39,19 @@ module NoFlyList
39
39
 
40
40
  def connection_abstract_class_name
41
41
  # should be abstract class name
42
- ActiveRecord::Base.descendants.find do |klass|
42
+ klass = ActiveRecord::Base.descendants.find do |klass|
43
43
  klass.abstract_class? && klass.connection_db_config.name == connection_name
44
- end.name
44
+ end
45
+ klass&.name || "ApplicationRecord"
45
46
  end
46
47
 
47
48
  def migration_version
48
49
  "[#{Rails::VERSION::MAJOR}.#{Rails::VERSION::MINOR}]"
49
50
  end
51
+
52
+ def migration_class_name
53
+ "CreateApplicationTaggingTable"
54
+ end
50
55
  end
51
56
  end
52
57
  end
@@ -36,18 +36,17 @@ module NoFlyList
36
36
  if model_class < ActiveRecord::Base
37
37
  true
38
38
  else
39
- say "#{class_name} is not an ActiveRecord model. Aborting generator.", :red
40
- false
39
+ raise ArgumentError, "#{class_name} is not an ActiveRecord model. Aborting generator."
41
40
  end
42
41
  rescue NameError
43
- say "#{class_name} is not a valid constant. Aborting generator.", :red
44
- false
42
+ raise ArgumentError, "#{class_name} is not a valid constant. Aborting generator."
45
43
  end
46
44
 
47
45
  def model_abstract_class_name
48
- model_class.ancestors.find do |klass|
49
- klass.is_a?(Class) && klass.abstract_class?
50
- end.name
46
+ klass = model_class.ancestors.find do |ancestor|
47
+ ancestor.is_a?(Class) && ancestor.abstract_class?
48
+ end
49
+ klass&.name || "ApplicationRecord"
51
50
  end
52
51
  end
53
52
  end
@@ -9,6 +9,7 @@ module NoFlyList
9
9
  module Generators
10
10
  class TaggingGenerator < Rails::Generators::NamedBase
11
11
  include ActiveRecord::Generators::Migration
12
+ source_root File.expand_path("templates", __dir__)
12
13
 
13
14
  class_option :database, type: :string, default: "primary",
14
15
  desc: "Use different database for migration"
@@ -5,15 +5,14 @@ require "rails/generators"
5
5
  require "rails/generators/active_record"
6
6
  require "rails/generators/named_base"
7
7
 
8
- unless defined?(ApplicationTagTransformer)
9
- module NoFlyList
10
- module Generators
11
- # bin/rails g no_fly_list:transformer
12
- class TransformerGenerator < Rails::Generators::Base
13
- source_root File.expand_path("templates", __dir__)
14
- def create_tag_transformer_file
15
- template "tag_transformer.rb", File.join("app/transformers", "application_tag_transformer.rb")
16
- end
8
+ module NoFlyList
9
+ module Generators
10
+ # bin/rails g no_fly_list:transformer
11
+ class TransformerGenerator < Rails::Generators::Base
12
+ source_root File.expand_path("templates", __dir__)
13
+
14
+ def create_tag_transformer_file
15
+ template "tag_transformer.rb", File.join("app/transformers", "application_tag_transformer.rb")
17
16
  end
18
17
  end
19
18
  end
@@ -0,0 +1,25 @@
1
+ # frozen_string_literal: true
2
+
3
+ module NoFlyList
4
+ module DefaultTransformer
5
+ module_function
6
+
7
+ # @param [String, Array<String>] tags
8
+ def parse_tags(tags)
9
+ tags = recreate_string(tags) if tags.is_a?(Array)
10
+ tags.split(separator).map(&:strip)
11
+ end
12
+
13
+ # Recreate a string from an array of tags
14
+ # @param [Array<String>] tags
15
+ # @return [String]
16
+ def recreate_string(tags)
17
+ tags.join(separator)
18
+ end
19
+
20
+ # @return [String]
21
+ def separator
22
+ ","
23
+ end
24
+ end
25
+ end
@@ -20,7 +20,7 @@ namespace :no_fly_list do
20
20
 
21
21
  classes.each do |klass|
22
22
  color = NoFlyList::TaskHelpers.adapter_color(klass)
23
- type = klass.included_modules.include?(NoFlyList::ApplicationTag) ? 'Global' : 'Model-specific'
23
+ type = klass.included_modules.include?(NoFlyList::ApplicationTag) ? "Global" : "Model-specific"
24
24
 
25
25
  puts "#{color}#{klass.name}#{NoFlyList::TaskHelpers::COLORS[:reset]}"
26
26
  puts " Type: #{type}"
@@ -42,8 +42,8 @@ namespace :no_fly_list do
42
42
  puts " #{message}"
43
43
 
44
44
  [
45
- ["#{klass.name}Tag", "Tags", :tag],
46
- ["#{klass.name}::Tagging", "Taggings", :tagging]
45
+ [ "#{klass.name}Tag", "Tags", :tag ],
46
+ [ "#{klass.name}::Tagging", "Taggings", :tagging ]
47
47
  ].each do |class_name, type, column_type|
48
48
  if (check_class = NoFlyList::TaskHelpers.check_class(class_name))
49
49
  status, message = NoFlyList::TaskHelpers.check_table(check_class)
@@ -53,13 +53,13 @@ namespace :no_fly_list do
53
53
  puts " #{NoFlyList::TaskHelpers.format_columns(check_class)}"
54
54
  end
55
55
  else
56
- puts " #{NoFlyList::TaskHelpers::colorize('✗', :red)} #{type} class not found: #{class_name}"
56
+ puts " #{NoFlyList::TaskHelpers.colorize('✗', :red)} #{type} class not found: #{class_name}"
57
57
  end
58
58
  end
59
59
 
60
60
  klass._no_fly_list.tag_contexts.each do |context, config|
61
61
  puts "\n Context: #{context}"
62
- bullet = NoFlyList::TaskHelpers::colorize('', :green)
62
+ bullet = NoFlyList::TaskHelpers.colorize("", :green)
63
63
  puts " #{bullet} Tag class: #{config[:tag_class_name]}"
64
64
  puts " #{bullet} Tagging class: #{config[:tagging_class_name]}"
65
65
  puts " #{bullet} Polymorphic: #{config[:polymorphic]}"
@@ -19,7 +19,7 @@ module NoFlyList
19
19
  taggable_class: @taggable_class.to_s,
20
20
  tag_class_name: tag_class_name,
21
21
  tagging_class_name: tagging_class_name,
22
- transformer: options.fetch(:transformer, ApplicationTagTransformer).to_s,
22
+ transformer: options.fetch(:transformer, "ApplicationTagTransformer").to_s,
23
23
  polymorphic: options.fetch(:polymorphic, false),
24
24
  restrict_to_existing: options.fetch(:restrict_to_existing, false),
25
25
  limit: options.fetch(:limit, nil),
@@ -41,7 +41,7 @@ module NoFlyList
41
41
  def initialize(taggable_klass, context, options = {})
42
42
  @taggable_klass = taggable_klass
43
43
  @context = context
44
- @transformer = options.fetch(:transformer, ApplicationTagTransformer)
44
+ @transformer = options.fetch(:transformer, "ApplicationTagTransformer")
45
45
  @polymorphic = options.fetch(:polymorphic, false)
46
46
  @restrict_to_existing = options.fetch(:restrict_to_existing, false)
47
47
  @counter_cache = options.fetch(:counter_cache, false)
@@ -1,5 +1,3 @@
1
- # frozen_string_literal: true
2
-
3
1
  module NoFlyList
4
2
  class TaggingProxy
5
3
  include Enumerable
@@ -21,23 +19,37 @@ module NoFlyList
21
19
  # @param restrict_to_existing [Boolean] Only allow existing tags
22
20
  # @param limit [Integer, nil] Maximum number of tags allowed
23
21
  def initialize(model, tag_model, context,
24
- transformer: ApplicationTagTransformer,
22
+ transformer: "ApplicationTagTransformer",
25
23
  restrict_to_existing: false,
26
24
  limit: nil)
27
25
  @model = model
28
26
  @tag_model = tag_model
29
27
  @context = context
30
- @transformer = transformer.is_a?(String) ? transformer.constantize : transformer
28
+ @transformer = resolve_transformer(transformer)
31
29
  @restrict_to_existing = restrict_to_existing
32
30
  @limit = limit
33
- @pending_changes = []
31
+ @pending_changes = nil # Use nil to indicate no changes yet
32
+ @clear_operation = false
33
+ end
34
+
35
+ def resolve_transformer(trans)
36
+ const = trans
37
+ const = const.constantize if const.is_a?(String)
38
+ unless const.respond_to?(:parse_tags) && const.respond_to?(:recreate_string)
39
+ warn "NoFlyList: transformer #{trans.inspect} is invalid. Falling back to DefaultTransformer"
40
+ const = NoFlyList::DefaultTransformer
41
+ end
42
+ const
43
+ rescue NameError
44
+ warn "NoFlyList: transformer #{trans.inspect} not found. Falling back to DefaultTransformer"
45
+ NoFlyList::DefaultTransformer
34
46
  end
35
47
 
36
48
  # Determines if tags have changed from database state
37
49
  # @return [Boolean] True if pending changes differ from database
38
50
  # @api private
39
51
  def changed?
40
- @pending_changes.present? && @pending_changes != current_list_from_database
52
+ @clear_operation || (!@pending_changes.nil? && @pending_changes != current_list_from_database)
41
53
  end
42
54
 
43
55
  def method_missing(method_name, *args)
@@ -73,7 +85,7 @@ module NoFlyList
73
85
 
74
86
  # @return [Boolean] true if the proxy is valid
75
87
  def save
76
- return true unless @pending_changes.any?
88
+ return true unless changed?
77
89
  return false unless valid?
78
90
 
79
91
  # Prevent recursive validation
@@ -92,8 +104,9 @@ module NoFlyList
92
104
 
93
105
  # Update counter
94
106
  model.update_column("#{@context}_count", 0) if setup[:counter_cache]
107
+
95
108
  # Create new tags
96
- @pending_changes.each do |tag_name|
109
+ pending_list.each do |tag_name|
97
110
  tag = find_or_create_tag(tag_name)
98
111
  next unless tag
99
112
 
@@ -112,7 +125,7 @@ module NoFlyList
112
125
  end
113
126
  end
114
127
  # Update counter to match the actual count
115
- model.update_column("#{@context}_count", @pending_changes.size) if setup[:counter_cache]
128
+ model.update_column("#{@context}_count", pending_list.size) if setup[:counter_cache]
116
129
 
117
130
  refresh_from_database
118
131
  true
@@ -133,15 +146,22 @@ module NoFlyList
133
146
 
134
147
  # @return [Integer]
135
148
  def count
149
+ # Always return the database count for count operations
136
150
  @model.send(@context.to_s).count
137
151
  end
138
152
 
139
153
  # @return [Integer]
140
154
  def size
141
- if @pending_changes.any?
155
+ # For size, return the database count if we've had a validation error
156
+ if !valid?
157
+ count
158
+ # Otherwise show pending changes
159
+ elsif @clear_operation
160
+ 0
161
+ elsif !@pending_changes.nil?
142
162
  @pending_changes.size
143
163
  else
144
- @model.send(@context.to_s).size
164
+ count
145
165
  end
146
166
  end
147
167
 
@@ -160,9 +180,44 @@ module NoFlyList
160
180
  @transformer_name ||= transformer.name
161
181
  end
162
182
 
183
+ # Returns tags that will be added (not in database but in pending changes)
184
+ # @return [Array<String>] Tags to be added
185
+ def additions
186
+ return [] if @clear_operation
187
+ return [] if @pending_changes.nil?
188
+
189
+ @pending_changes - current_list_from_database
190
+ end
191
+
192
+ # Returns tags that will be removed (in database but not in pending changes)
193
+ # @return [Array<String>] Tags to be removed
194
+ def removals
195
+ if @clear_operation
196
+ current_list_from_database
197
+ elsif @pending_changes.nil?
198
+ []
199
+ else
200
+ current_list_from_database - @pending_changes
201
+ end
202
+ end
203
+
163
204
  # @return [String]
164
205
  def inspect
165
- "#<#{self.class.name} tags=#{current_list.inspect} transformer_with=#{transformer_name} >"
206
+ if @clear_operation
207
+ db_tags = current_list_from_database
208
+ "#<#{self.class.name} tags=[] changes=[CLEARING ALL (#{db_tags.size}): #{db_tags.inspect}] transformer_with=#{transformer_name}>"
209
+ elsif !@pending_changes.nil?
210
+ add_list = additions
211
+ remove_list = removals
212
+ changes = []
213
+ changes << "+#{add_list.inspect}" if add_list.any?
214
+ changes << "-#{remove_list.inspect}" if remove_list.any?
215
+ changes_str = changes.join(", ")
216
+
217
+ "#<#{self.class.name} tags=#{current_list.inspect} changes=[#{changes_str}] transformer_with=#{transformer_name}>"
218
+ else
219
+ "#<#{self.class.name} tags=#{current_list.inspect} transformer_with=#{transformer_name}>"
220
+ end
166
221
  end
167
222
 
168
223
  # Adds one or more tags to the current tag list
@@ -174,6 +229,7 @@ module NoFlyList
174
229
  def add(*tags)
175
230
  return self if limit_reached?
176
231
 
232
+ @clear_operation = false
177
233
  new_tags = if tags.size == 1 && tags.first.is_a?(String)
178
234
  transformer.parse_tags(tags.first)
179
235
  else
@@ -181,8 +237,12 @@ module NoFlyList
181
237
  end
182
238
  return self if new_tags.empty?
183
239
 
184
- @pending_changes = current_list + new_tags
240
+ # Initialize @pending_changes with database values if not yet initialized
241
+ @pending_changes = current_list_from_database if @pending_changes.nil?
242
+
243
+ @pending_changes = @pending_changes + new_tags
185
244
  @pending_changes.uniq!
245
+ mark_record_dirty
186
246
  self
187
247
  end
188
248
 
@@ -199,13 +259,20 @@ module NoFlyList
199
259
  # @return [TaggingProxy] Returns self for method chaining
200
260
  # @raise [ActiveRecord::RecordInvalid] If validation fails
201
261
  def remove(*tags)
202
- old_list = current_list.dup
262
+ @clear_operation = false
263
+
264
+ # Initialize @pending_changes with database values if not yet initialized
265
+ @pending_changes = current_list_from_database if @pending_changes.nil?
266
+
267
+ old_list = @pending_changes.dup
268
+
203
269
  tags_to_remove = if tags.size == 1 && tags.first.is_a?(String)
204
270
  transformer.parse_tags(tags.first)
205
271
  else
206
272
  tags.flatten.map { |tag| tag.to_s.strip }
207
273
  end
208
- @pending_changes = current_list - tags_to_remove
274
+
275
+ @pending_changes = @pending_changes - tags_to_remove
209
276
  mark_record_dirty if @pending_changes != old_list
210
277
  self
211
278
  end
@@ -220,9 +287,9 @@ module NoFlyList
220
287
  # @example Clear all tags
221
288
  # tags.clear #=> []
222
289
  def clear
223
- old_list = current_list.dup
290
+ @clear_operation = true
224
291
  @pending_changes = []
225
- mark_record_dirty if @pending_changes != old_list
292
+ mark_record_dirty if current_list_from_database.any?
226
293
  model.write_attribute("#{@context}_count", 0) if setup[:counter_cache]
227
294
  self
228
295
  end
@@ -235,6 +302,7 @@ module NoFlyList
235
302
  def clear!
236
303
  @model.send(@context.to_s).destroy_all
237
304
  @pending_changes = []
305
+ @clear_operation = false
238
306
  @model.update_column("#{@context}_count", 0) if setup[:counter_cache]
239
307
  self
240
308
  end
@@ -276,7 +344,9 @@ module NoFlyList
276
344
  end
277
345
 
278
346
  def set_list(_context, value)
347
+ @clear_operation = false
279
348
  @pending_changes = transformer.parse_tags(value)
349
+ mark_record_dirty
280
350
  valid? # Just check validity without raising
281
351
  self
282
352
  end
@@ -286,24 +356,25 @@ module NoFlyList
286
356
  end
287
357
 
288
358
  def refresh_from_database
289
- @pending_changes = []
359
+ @pending_changes = nil
360
+ @clear_operation = false
290
361
  end
291
362
 
292
363
  def validate_limit
293
364
  return unless @limit
294
- return if @pending_changes.size <= @limit
365
+ return if pending_list.size <= @limit
295
366
 
296
- errors.add(:base, "Cannot have more than #{@limit} tags (attempting to save #{@pending_changes.size})")
367
+ errors.add(:base, "Cannot have more than #{@limit} tags (attempting to save #{pending_list.size})")
297
368
  end
298
369
 
299
370
  def validate_existing_tags
300
371
  return unless @restrict_to_existing
301
- return if @pending_changes.empty?
372
+ return if pending_list.empty?
302
373
 
303
374
  # Transform tags to lowercase for comparison
304
- normalized_changes = @pending_changes.map(&:downcase)
375
+ normalized_changes = pending_list.map(&:downcase)
305
376
  existing_tags = @tag_model.where("LOWER(name) IN (?)", normalized_changes).pluck(:name)
306
- missing_tags = @pending_changes - existing_tags
377
+ missing_tags = pending_list - existing_tags
307
378
 
308
379
  return unless missing_tags.any?
309
380
 
@@ -316,9 +387,9 @@ module NoFlyList
316
387
 
317
388
  def setup
318
389
  @setup ||= begin
319
- context = @context.to_sym
320
- @model.class._no_fly_list.tag_contexts[context]
321
- end
390
+ context = @context.to_sym
391
+ @model.class._no_fly_list.tag_contexts[context]
392
+ end
322
393
  end
323
394
 
324
395
  def find_or_create_tag(tag_name)
@@ -329,36 +400,24 @@ module NoFlyList
329
400
  end
330
401
  end
331
402
 
332
- def save_changes
333
- # Clear existing tags
334
- model.send(context_taggings).delete_all
335
-
336
- # Create new tags
337
- @pending_changes.each do |tag_name|
338
- tag = find_or_create_tag(tag_name)
339
- next unless tag
340
-
341
- attributes = {
342
- tag: tag,
343
- context: @context.to_s.singularize
344
- }
345
-
346
- # Add polymorphic attributes for polymorphic tags
347
- if setup[:polymorphic]
348
- attributes[:taggable_type] = model.class.name
349
- attributes[:taggable_id] = model.id
350
- end
351
-
352
- # Use create! to ensure we catch any errors
353
- model.send(context_taggings).create!(attributes)
403
+ # Helper method to get the list of tags that should be saved
404
+ def pending_list
405
+ if @clear_operation
406
+ []
407
+ elsif !@pending_changes.nil?
408
+ @pending_changes
409
+ else
410
+ current_list_from_database
354
411
  end
355
-
356
- refresh_from_database
357
- true
358
412
  end
359
413
 
360
414
  def current_list
361
- if @pending_changes.any?
415
+ # If validation failed, always return what's in the database
416
+ if errors.any?
417
+ current_list_from_database
418
+ elsif @clear_operation
419
+ []
420
+ elsif !@pending_changes.nil?
362
421
  @pending_changes
363
422
  else
364
423
  current_list_from_database
@@ -13,8 +13,8 @@ module NoFlyList
13
13
  }.freeze
14
14
 
15
15
  REQUIRED_COLUMNS = {
16
- tag: ['name'],
17
- tagging: ['tag_id', 'taggable_id', 'context']
16
+ tag: [ "name" ],
17
+ tagging: %w[tag_id taggable_id context]
18
18
  }.freeze
19
19
 
20
20
  def self.adapter_color(klass)
@@ -28,9 +28,9 @@ module NoFlyList
28
28
 
29
29
  def self.check_table(klass)
30
30
  klass.table_exists?
31
- [true, "#{colorize('✓', :green)} Table exists: #{klass.table_name}"]
31
+ [ true, "#{colorize('✓', :green)} Table exists: #{klass.table_name}" ]
32
32
  rescue StandardError => e
33
- [false, "#{colorize('✗', :red)} Error: #{e.message}"]
33
+ [ false, "#{colorize('✗', :red)} Error: #{e.message}" ]
34
34
  end
35
35
 
36
36
  def self.verify_columns(klass, type)
@@ -61,16 +61,15 @@ module NoFlyList
61
61
  def self.find_taggable_classes
62
62
  Rails.application.eager_load!
63
63
  ActiveRecord::Base.descendants.select do |klass|
64
- klass.included_modules.any? { |mod| mod.in?([NoFlyList::TaggableRecord]) }
64
+ klass.included_modules.any? { |mod| mod.in?([ NoFlyList::TaggableRecord ]) }
65
65
  end
66
66
  end
67
67
 
68
68
  def self.find_tag_classes
69
69
  Rails.application.eager_load!
70
70
  ActiveRecord::Base.descendants.select do |klass|
71
- klass.included_modules.any? { |mod| mod.in?([NoFlyList::ApplicationTag, NoFlyList::TagRecord]) }
71
+ klass.included_modules.any? { |mod| mod.in?([ NoFlyList::ApplicationTag, NoFlyList::TagRecord ]) }
72
72
  end
73
73
  end
74
74
  end
75
75
  end
76
-
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module NoFlyList
4
- VERSION = "0.6.0"
4
+ VERSION = "0.7.2"
5
5
  end
data/lib/no_fly_list.rb CHANGED
@@ -28,6 +28,7 @@ module NoFlyList
28
28
 
29
29
  autoload :TaggingRecord
30
30
  autoload :TagRecord
31
+ autoload :DefaultTransformer
31
32
 
32
33
  autoload :TaggingProxy
33
34
 
metadata CHANGED
@@ -1,14 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: no_fly_list
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.6.0
4
+ version: 0.7.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - Abdelkader Boudih
8
- autorequire:
9
8
  bindir: bin
10
9
  cert_chain: []
11
- date: 2024-12-20 00:00:00.000000000 Z
10
+ date: 1980-01-02 00:00:00.000000000 Z
12
11
  dependencies:
13
12
  - !ruby/object:Gem::Dependency
14
13
  name: activerecord
@@ -45,6 +44,7 @@ files:
45
44
  - lib/no_fly_list.rb
46
45
  - lib/no_fly_list/application_tag.rb
47
46
  - lib/no_fly_list/application_tagging.rb
47
+ - lib/no_fly_list/default_transformer.rb
48
48
  - lib/no_fly_list/railtie.rb
49
49
  - lib/no_fly_list/railties/tasks.rake
50
50
  - lib/no_fly_list/tag_record.rb
@@ -67,7 +67,6 @@ licenses:
67
67
  - MIT
68
68
  metadata:
69
69
  rubygems_mfa_required: 'true'
70
- post_install_message:
71
70
  rdoc_options: []
72
71
  require_paths:
73
72
  - lib
@@ -82,8 +81,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
82
81
  - !ruby/object:Gem::Version
83
82
  version: '0'
84
83
  requirements: []
85
- rubygems_version: 3.5.22
86
- signing_key:
84
+ rubygems_version: 3.6.9
87
85
  specification_version: 4
88
86
  summary: Tagging system for ActiveRecord models
89
87
  test_files: []