magick-feature-flags 0.8.8 → 0.9.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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 876436714b054435d68ac40f18eab6597165640e5f4ab2cb666474f7b03cb92f
4
- data.tar.gz: 1cb04e84837d1faf72fa9566fe852ce484d20035b763b9cec4896ec1cb24b62e
3
+ metadata.gz: cb4c8735b5c0df6cc7331ddd6cb4bec60b7557839dbe38087c61b5c3ac7a434e
4
+ data.tar.gz: 1035c662c99663e07265a6e25f5cccfaa833057bac07b3dd7b9739f15916ece2
5
5
  SHA512:
6
- metadata.gz: b541dbee500ab1e93969791326ca2f02ab7b4bd9595f5a903ec954018166cf5de9f26cde857325e2698fdcfe311533e31f3eb201027594e4a66007246a14248a
7
- data.tar.gz: 701320125c33d03df6238e010ee9ce274f59fc56d4b423ebb6ffec131b2edda19fb1214dc532b875259f63848e4cbfa61ddbbf9b1354b6384fa139cd17c06840
6
+ metadata.gz: 5d42c95ef3ea3e5b2a96788970df810d18fc8bad3c73efb87dd6ec056a6eb1518d20bee97a3940faf302f432deb524b98529dd350bc0b2ed83796fcb78ffbd6c
7
+ data.tar.gz: a0753994c42679b82438fe6d9b6f9a1d993b1efd151cf93a2a027ee23c1b8355945a62d32421aee55d8fecd61eb810b9638eb7d237b6fb9e4d10309905dbf9dc
@@ -20,6 +20,7 @@ module Magick
20
20
  @display_name = options[:name] || options[:display_name]
21
21
  @targeting = {}
22
22
  @dependencies = options[:dependencies] ? Array(options[:dependencies]) : []
23
+ @stored_value_initialized = false # Track if @stored_value has been explicitly set
23
24
 
24
25
  validate_type!
25
26
  validate_default_value!
@@ -64,7 +65,9 @@ module Magick
64
65
  duration = (Time.now - start_time) * 1000
65
66
  Magick.performance_metrics.record(name, 'enabled?', duration, success: false)
66
67
  end
67
- raise e
68
+ # Return false on any error (fail-safe)
69
+ warn "Magick: Error checking feature '#{name}': #{e.message}" if defined?(Rails) && Rails.env.development?
70
+ false
68
71
  end
69
72
 
70
73
  def check_enabled(context = {})
@@ -99,6 +102,10 @@ module Magick
99
102
  else
100
103
  false
101
104
  end
105
+ rescue StandardError => e
106
+ # Return false on any error (fail-safe)
107
+ warn "Magick: Error in check_enabled for '#{name}': #{e.message}" if defined?(Rails) && Rails.env.development?
108
+ false
102
109
  end
103
110
 
104
111
  def disabled?(context = {})
@@ -126,11 +133,26 @@ module Magick
126
133
  targeting_result = check_targeting(context)
127
134
  return targeting_result unless targeting_result.nil?
128
135
 
129
- # Use instance variable if set, otherwise load from adapter
130
- # This ensures we use the most recent value set via set_value/disable/enable
131
- value = @stored_value
132
- value = load_value_from_adapter if value.nil?
133
- value || default_value
136
+ # Use instance variable if it has been set (check using defined? to handle nil vs uninitialized)
137
+ # We use a special check: if @stored_value was explicitly set (even to false), use it
138
+ # We track this by checking if @stored_value_initialized flag is set
139
+ return @stored_value if defined?(@stored_value_initialized) && @stored_value_initialized
140
+
141
+ # Load from adapter if instance variable hasn't been initialized
142
+ loaded_value = load_value_from_adapter
143
+ if loaded_value.nil?
144
+ # Value not found in adapter, use default
145
+ default_value
146
+ else
147
+ # Value found in adapter, use it and mark as initialized
148
+ @stored_value = loaded_value
149
+ @stored_value_initialized = true
150
+ loaded_value
151
+ end
152
+ rescue StandardError => e
153
+ # Return default value on error (fail-safe)
154
+ warn "Magick: Error in get_value for '#{name}': #{e.message}" if defined?(Rails) && Rails.env.development?
155
+ default_value
134
156
  end
135
157
 
136
158
  def enable_for_user(user_id)
@@ -326,11 +348,13 @@ module Magick
326
348
  adapter_registry.set(name, 'description', description) if description
327
349
  adapter_registry.set(name, 'display_name', display_name) if display_name
328
350
  @stored_value = value
351
+ @stored_value_initialized = true # Mark as initialized
329
352
 
330
353
  # Update registered feature instance if it exists
331
354
  if Magick.features.key?(name)
332
355
  registered = Magick.features[name]
333
356
  registered.instance_variable_set(:@stored_value, value)
357
+ registered.instance_variable_set(:@stored_value_initialized, true)
334
358
  registered.instance_variable_set(:@targeting, @targeting.dup) if @targeting
335
359
  end
336
360
 
@@ -434,6 +458,7 @@ module Magick
434
458
  if Magick.features.key?(name)
435
459
  registered = Magick.features[name]
436
460
  registered.instance_variable_set(:@stored_value, @stored_value)
461
+ registered.instance_variable_set(:@stored_value_initialized, @stored_value_initialized)
437
462
  registered.instance_variable_set(:@status, @status)
438
463
  registered.instance_variable_set(:@description, @description)
439
464
  registered.instance_variable_set(:@display_name, @display_name)
@@ -466,19 +491,31 @@ module Magick
466
491
  end
467
492
 
468
493
  def load_from_adapter
469
- # Clear cached value to force reload from adapter (which checks version)
470
- @stored_value = nil
471
- @stored_value = load_value_from_adapter
494
+ # Load value from adapter
495
+ loaded_value = load_value_from_adapter
496
+ # Set @stored_value if we got a value from adapter (can be false, true, '', 0, etc.)
497
+ # Only set if loaded_value is not nil (nil means not found in adapter)
498
+ unless loaded_value.nil?
499
+ @stored_value = loaded_value
500
+ @stored_value_initialized = true
501
+ end
502
+
472
503
  status_value = adapter_registry.get(name, 'status')
473
504
  @status = status_value ? status_value.to_sym : status
474
505
 
475
- # Load description from adapter (override initial value if present in adapter)
476
- description_value = adapter_registry.get(name, 'description')
477
- @description = description_value if description_value
506
+ # Load description from adapter only if not provided in DSL
507
+ # DSL (features.rb) is the source of truth, so don't override DSL values
508
+ unless @description
509
+ description_value = adapter_registry.get(name, 'description')
510
+ @description = description_value if description_value
511
+ end
478
512
 
479
- # Load display_name from adapter (override initial value if present in adapter)
480
- display_name_value = adapter_registry.get(name, 'display_name')
481
- @display_name = display_name_value if display_name_value
513
+ # Load display_name from adapter only if not provided in DSL
514
+ # DSL (features.rb) is the source of truth, so don't override DSL values
515
+ unless @display_name
516
+ display_name_value = adapter_registry.get(name, 'display_name')
517
+ @display_name = display_name_value if display_name_value
518
+ end
482
519
 
483
520
  targeting_value = adapter_registry.get(name, 'targeting')
484
521
  if targeting_value.is_a?(Hash)
@@ -493,12 +530,11 @@ module Magick
493
530
  end
494
531
 
495
532
  def save_metadata_if_new
496
- # Save description and display_name to adapter if they were provided in options
497
- # but don't exist in adapter yet (to avoid overwriting existing values)
498
- if @description && !adapter_registry.get(name, 'description')
499
- adapter_registry.set(name, 'description', @description)
500
- end
501
- return unless @display_name && !adapter_registry.get(name, 'display_name')
533
+ # Always save description and display_name from DSL to adapter
534
+ # The features.rb file is the source of truth for metadata
535
+ # This ensures metadata is always up-to-date even if feature already exists
536
+ adapter_registry.set(name, 'description', @description) if @description
537
+ return unless @display_name
502
538
 
503
539
  adapter_registry.set(name, 'display_name', @display_name)
504
540
  end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Magick
4
- VERSION = '0.8.8'
4
+ VERSION = '0.9.1'
5
5
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: magick-feature-flags
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.8.8
4
+ version: 0.9.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Andrew Lobanov