Class: ConfigCat::RolloutEvaluator
- Inherits:
-
Object
- Object
- ConfigCat::RolloutEvaluator
- Defined in:
- lib/configcat/rolloutevaluator.rb
Instance Method Summary collapse
-
#evaluate(key:, user:, default_value:, default_variation_id:, config:, log_builder:, visited_keys: nil) ⇒ Object
:returns value, variation_id.
-
#initialize(log) ⇒ RolloutEvaluator
constructor
A new instance of RolloutEvaluator.
Constructor Details
#initialize(log) ⇒ RolloutEvaluator
Returns a new instance of RolloutEvaluator.
11 12 13 |
# File 'lib/configcat/rolloutevaluator.rb', line 11 def initialize(log) @log = log end |
Instance Method Details
#evaluate(key:, user:, default_value:, default_variation_id:, config:, log_builder:, visited_keys: nil) ⇒ Object
:returns value, variation_id. matched_targeting_rule, matched_percentage_option, error
16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 |
# File 'lib/configcat/rolloutevaluator.rb', line 16 def evaluate(key:, user:, default_value:, default_variation_id:, config:, log_builder:, visited_keys: nil) visited_keys ||= [] is_root_flag_evaluation = visited_keys.empty? settings = config[FEATURE_FLAGS] || {} setting_descriptor = settings[key] if setting_descriptor.nil? error = "Failed to evaluate setting '#{key}' (the key was not found in config JSON). " \ "Returning the `default_value` parameter that you specified in your application: '#{default_value}'. " \ "Available keys: [#{settings.keys.map { |s| "'#{s}'" }.join(", ")}]." @log.error(1001, error) return default_value, default_variation_id, nil, nil, error end setting_type = setting_descriptor[SETTING_TYPE] salt = setting_descriptor[INLINE_SALT] || '' targeting_rules = setting_descriptor[TARGETING_RULES] || [] percentage_rule_attribute = setting_descriptor[PERCENTAGE_RULE_ATTRIBUTE] context = EvaluationContext.new(key, setting_type, user, visited_keys) user_has_invalid_type = context.user && !context.user.is_a?(User) if user_has_invalid_type @log.warn(4001, "Cannot evaluate targeting rules and % options for setting '#{key}' " \ "(User Object is not an instance of User type). " \ "You should pass a User Object to the evaluation methods like `get_value()` " \ "in order to make targeting work properly. " \ "Read more: https://configcat.com/docs/advanced/user-object/") # We set the user to nil and won't log further missing user object warnings context.user = nil context.is_missing_user_object_logged = true end begin if log_builder && is_root_flag_evaluation log_builder.append("Evaluating '#{key}'") log_builder.append(" for User '#{context.user}'") if context.user log_builder.increase_indent end # Evaluate targeting rules (logically connected by OR) if log_builder && targeting_rules.any? log_builder.new_line("Evaluating targeting rules and applying the first match if any:") end targeting_rules.each do |targeting_rule| conditions = targeting_rule[CONDITIONS] || [] if conditions.any? served_value = targeting_rule[SERVED_VALUE] value = Config.get_value(served_value, setting_type) if served_value # Evaluate targeting rule conditions (logically connected by AND) if evaluate_conditions(conditions, context, salt, config, log_builder, value) if served_value variation_id = served_value[VARIATION_ID] || default_variation_id log_builder.new_line("Returning '#{value}'.") if log_builder && is_root_flag_evaluation return [value, variation_id, targeting_rule, nil, nil] end else next end end # Evaluate percentage options of the targeting rule log_builder&.increase_indent = targeting_rule.fetch(TARGETING_RULE_PERCENTAGE_OPTIONS, []) percentage_evaluation_result, percentage_value, percentage_variation_id, percentage_option = (, context, percentage_rule_attribute, default_variation_id, log_builder) if percentage_evaluation_result if log_builder log_builder.decrease_indent log_builder.new_line("Returning '#{percentage_value}'.") if is_root_flag_evaluation end return [percentage_value, percentage_variation_id, targeting_rule, percentage_option, nil] else if log_builder log_builder.new_line('The current targeting rule is ignored and the evaluation continues with the next rule.') log_builder.decrease_indent end next end end # Evaluate percentage options = setting_descriptor.fetch(PERCENTAGE_OPTIONS, []) percentage_evaluation_result, percentage_value, percentage_variation_id, percentage_option = (, context, percentage_rule_attribute, default_variation_id, log_builder) if percentage_evaluation_result log_builder.new_line("Returning '#{percentage_value}'.") if log_builder && is_root_flag_evaluation return [percentage_value, percentage_variation_id, nil, percentage_option, nil] end return_value = Config.get_value(setting_descriptor, setting_type) return_variation_id = setting_descriptor.fetch(VARIATION_ID, default_variation_id) log_builder.new_line("Returning '#{return_value}'.") if log_builder && is_root_flag_evaluation return [return_value, return_variation_id, nil, nil, nil] rescue => e # During the recursive evaluation of a prerequisite flag, we propagate the exceptions # and let the root flag's evaluation code handle them. if !is_root_flag_evaluation raise e else error = "Failed to evaluate setting '#{key}'. (#{e}). " \ "Returning the `%s` parameter that you specified in your application: '#{default_value}'." @log.error(2001, error) return [default_value, default_variation_id, nil, nil, error] end end end |