prefab-cloud-ruby 0.24.2 → 0.24.4

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 (44) hide show
  1. checksums.yaml +4 -4
  2. data/.github/workflows/ruby.yml +1 -1
  3. data/.rubocop.yml +13 -0
  4. data/CHANGELOG.md +76 -0
  5. data/Gemfile.lock +4 -4
  6. data/VERSION +1 -1
  7. data/bin/console +21 -0
  8. data/compile_protos.sh +6 -0
  9. data/lib/prefab/client.rb +25 -4
  10. data/lib/prefab/config_client.rb +16 -6
  11. data/lib/prefab/config_loader.rb +1 -1
  12. data/lib/prefab/config_resolver.rb +2 -4
  13. data/lib/prefab/config_value_wrapper.rb +18 -0
  14. data/lib/prefab/context.rb +22 -2
  15. data/lib/prefab/context_shape.rb +20 -0
  16. data/lib/prefab/context_shape_aggregator.rb +63 -0
  17. data/lib/prefab/criteria_evaluator.rb +61 -41
  18. data/lib/prefab/evaluated_configs_aggregator.rb +60 -0
  19. data/lib/prefab/evaluated_keys_aggregator.rb +41 -0
  20. data/lib/prefab/local_config_parser.rb +13 -13
  21. data/lib/prefab/log_path_aggregator.rb +64 -0
  22. data/lib/prefab/logger_client.rb +29 -16
  23. data/lib/prefab/options.rb +46 -1
  24. data/lib/prefab/periodic_sync.rb +51 -0
  25. data/lib/prefab/time_helpers.rb +7 -0
  26. data/lib/prefab-cloud-ruby.rb +8 -1
  27. data/lib/prefab_pb.rb +33 -220
  28. data/prefab-cloud-ruby.gemspec +21 -5
  29. data/test/test_config_loader.rb +15 -15
  30. data/test/test_config_resolver.rb +102 -102
  31. data/test/test_config_value_unwrapper.rb +13 -13
  32. data/test/test_context.rb +42 -0
  33. data/test/test_context_shape.rb +51 -0
  34. data/test/test_context_shape_aggregator.rb +137 -0
  35. data/test/test_criteria_evaluator.rb +253 -150
  36. data/test/test_evaluated_configs_aggregator.rb +254 -0
  37. data/test/test_evaluated_keys_aggregator.rb +54 -0
  38. data/test/test_helper.rb +34 -2
  39. data/test/test_log_path_aggregator.rb +57 -0
  40. data/test/test_logger.rb +61 -76
  41. data/test/test_weighted_value_resolver.rb +2 -2
  42. metadata +21 -5
  43. data/lib/prefab/log_path_collector.rb +0 -102
  44. data/test/test_log_path_collector.rb +0 -58
@@ -1,6 +1,7 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  require 'test_helper'
4
+ require 'timecop'
4
5
 
5
6
  class TestCriteriaEvaluator < Minitest::Test
6
7
  PROJECT_ENV_ID = 1
@@ -10,63 +11,61 @@ class TestCriteriaEvaluator < Minitest::Test
10
11
  DESIRED_VALUE = 'desired_value'
11
12
  WRONG_ENV_VALUE = 'wrong_env_value'
12
13
 
13
- DEFAULT_ROW = Prefab::ConfigRow.new(
14
+ DEFAULT_ROW = PrefabProto::ConfigRow.new(
14
15
  values: [
15
- Prefab::ConditionalValue.new(
16
- value: Prefab::ConfigValue.new(string: DEFAULT_VALUE)
16
+ PrefabProto::ConditionalValue.new(
17
+ value: PrefabProto::ConfigValue.new(string: DEFAULT_VALUE)
17
18
  )
18
19
  ]
19
20
  )
20
21
 
21
22
  def test_always_true
22
- config = Prefab::Config.new(
23
+ config = PrefabProto::Config.new(
23
24
  key: KEY,
24
25
  rows: [
25
26
  DEFAULT_ROW,
26
- Prefab::ConfigRow.new(
27
+ PrefabProto::ConfigRow.new(
27
28
  project_env_id: PROJECT_ENV_ID,
28
29
  values: [
29
- Prefab::ConditionalValue.new(
30
- criteria: [
31
- Prefab::Criterion.new(operator: Prefab::Criterion::CriterionOperator::ALWAYS_TRUE)
32
- ],
33
- value: Prefab::ConfigValue.new(string: DESIRED_VALUE)
30
+ PrefabProto::ConditionalValue.new(
31
+ criteria: [PrefabProto::Criterion.new(operator: PrefabProto::Criterion::CriterionOperator::ALWAYS_TRUE)],
32
+ value: PrefabProto::ConfigValue.new(string: DESIRED_VALUE)
34
33
  )
35
34
  ]
36
35
  )
37
36
  ]
38
37
  )
39
38
 
40
- evaluator = Prefab::CriteriaEvaluator.new(config, project_env_id: PROJECT_ENV_ID, resolver: nil, base_client: nil,
39
+ evaluator = Prefab::CriteriaEvaluator.new(config, project_env_id: PROJECT_ENV_ID, resolver: nil, base_client: FakeBaseClient.new,
41
40
  namespace: nil)
42
41
 
43
42
  assert_equal DESIRED_VALUE, evaluator.evaluate(context({})).string
44
43
  end
45
44
 
46
45
  def test_nested_props_in
47
- config = Prefab::Config.new(
46
+ config = PrefabProto::Config.new(
48
47
  key: KEY,
49
48
  rows: [
50
49
  DEFAULT_ROW,
51
- Prefab::ConfigRow.new(
50
+ PrefabProto::ConfigRow.new(
52
51
  project_env_id: PROJECT_ENV_ID,
53
52
  values: [
54
- Prefab::ConditionalValue.new(
53
+ PrefabProto::ConditionalValue.new(
55
54
  criteria: [
56
- Prefab::Criterion.new(
57
- operator: Prefab::Criterion::CriterionOperator::PROP_IS_ONE_OF,
55
+ PrefabProto::Criterion.new(
56
+ operator: PrefabProto::Criterion::CriterionOperator::PROP_IS_ONE_OF,
58
57
  value_to_match: string_list(%w[ok fine]),
59
58
  property_name: 'user.key'
60
59
  )
61
60
  ],
62
- value: Prefab::ConfigValue.new(string: DESIRED_VALUE)
61
+ value: PrefabProto::ConfigValue.new(string: DESIRED_VALUE)
63
62
  )
64
63
  ]
65
64
  )
66
65
  ]
67
66
  )
68
67
 
69
- evaluator = Prefab::CriteriaEvaluator.new(config, project_env_id: PROJECT_ENV_ID, resolver: nil, base_client: nil,
68
+ evaluator = Prefab::CriteriaEvaluator.new(config, project_env_id: PROJECT_ENV_ID, resolver: nil, base_client: FakeBaseClient.new,
70
69
  namespace: nil)
71
70
 
72
71
  assert_equal DEFAULT_VALUE, evaluator.evaluate(context({})).string
@@ -75,29 +74,29 @@ class TestCriteriaEvaluator < Minitest::Test
75
74
  end
76
75
 
77
76
  def test_nested_props_not_in
78
- config = Prefab::Config.new(
77
+ config = PrefabProto::Config.new(
79
78
  key: KEY,
80
79
  rows: [
81
80
  DEFAULT_ROW,
82
- Prefab::ConfigRow.new(
81
+ PrefabProto::ConfigRow.new(
83
82
  project_env_id: PROJECT_ENV_ID,
84
83
  values: [
85
- Prefab::ConditionalValue.new(
84
+ PrefabProto::ConditionalValue.new(
86
85
  criteria: [
87
- Prefab::Criterion.new(
88
- operator: Prefab::Criterion::CriterionOperator::PROP_IS_NOT_ONE_OF,
86
+ PrefabProto::Criterion.new(
87
+ operator: PrefabProto::Criterion::CriterionOperator::PROP_IS_NOT_ONE_OF,
89
88
  value_to_match: string_list(%w[wrong bad]),
90
89
  property_name: 'user.key'
91
90
  )
92
91
  ],
93
- value: Prefab::ConfigValue.new(string: DESIRED_VALUE)
92
+ value: PrefabProto::ConfigValue.new(string: DESIRED_VALUE)
94
93
  )
95
94
  ]
96
95
  )
97
96
  ]
98
97
  )
99
98
 
100
- evaluator = Prefab::CriteriaEvaluator.new(config, project_env_id: PROJECT_ENV_ID, resolver: nil, base_client: nil,
99
+ evaluator = Prefab::CriteriaEvaluator.new(config, project_env_id: PROJECT_ENV_ID, resolver: nil, base_client: FakeBaseClient.new,
101
100
  namespace: nil)
102
101
 
103
102
  assert_equal DESIRED_VALUE, evaluator.evaluate(context({})).string
@@ -106,29 +105,29 @@ class TestCriteriaEvaluator < Minitest::Test
106
105
  end
107
106
 
108
107
  def test_prop_is_one_of
109
- config = Prefab::Config.new(
108
+ config = PrefabProto::Config.new(
110
109
  key: KEY,
111
110
  rows: [
112
111
  DEFAULT_ROW,
113
- Prefab::ConfigRow.new(
112
+ PrefabProto::ConfigRow.new(
114
113
  project_env_id: PROJECT_ENV_ID,
115
114
  values: [
116
- Prefab::ConditionalValue.new(
115
+ PrefabProto::ConditionalValue.new(
117
116
  criteria: [
118
- Prefab::Criterion.new(
119
- operator: Prefab::Criterion::CriterionOperator::PROP_IS_ONE_OF,
117
+ PrefabProto::Criterion.new(
118
+ operator: PrefabProto::Criterion::CriterionOperator::PROP_IS_ONE_OF,
120
119
  value_to_match: string_list(['hotmail.com', 'gmail.com']),
121
120
  property_name: 'user.email_suffix'
122
121
  )
123
122
  ],
124
- value: Prefab::ConfigValue.new(string: DESIRED_VALUE)
123
+ value: PrefabProto::ConfigValue.new(string: DESIRED_VALUE)
125
124
  )
126
125
  ]
127
126
  )
128
127
  ]
129
128
  )
130
129
 
131
- evaluator = Prefab::CriteriaEvaluator.new(config, project_env_id: PROJECT_ENV_ID, resolver: nil, base_client: nil,
130
+ evaluator = Prefab::CriteriaEvaluator.new(config, project_env_id: PROJECT_ENV_ID, resolver: nil, base_client: FakeBaseClient.new,
132
131
  namespace: nil)
133
132
 
134
133
  assert_equal DEFAULT_VALUE, evaluator.evaluate(context({})).string
@@ -137,29 +136,29 @@ class TestCriteriaEvaluator < Minitest::Test
137
136
  end
138
137
 
139
138
  def test_prop_is_not_one_of
140
- config = Prefab::Config.new(
139
+ config = PrefabProto::Config.new(
141
140
  key: KEY,
142
141
  rows: [
143
142
  DEFAULT_ROW,
144
- Prefab::ConfigRow.new(
143
+ PrefabProto::ConfigRow.new(
145
144
  project_env_id: PROJECT_ENV_ID,
146
145
  values: [
147
- Prefab::ConditionalValue.new(
146
+ PrefabProto::ConditionalValue.new(
148
147
  criteria: [
149
- Prefab::Criterion.new(
150
- operator: Prefab::Criterion::CriterionOperator::PROP_IS_NOT_ONE_OF,
148
+ PrefabProto::Criterion.new(
149
+ operator: PrefabProto::Criterion::CriterionOperator::PROP_IS_NOT_ONE_OF,
151
150
  value_to_match: string_list(['hotmail.com', 'gmail.com']),
152
151
  property_name: 'user.email_suffix'
153
152
  )
154
153
  ],
155
- value: Prefab::ConfigValue.new(string: DESIRED_VALUE)
154
+ value: PrefabProto::ConfigValue.new(string: DESIRED_VALUE)
156
155
  )
157
156
  ]
158
157
  )
159
158
  ]
160
159
  )
161
160
 
162
- evaluator = Prefab::CriteriaEvaluator.new(config, project_env_id: PROJECT_ENV_ID, resolver: nil, base_client: nil,
161
+ evaluator = Prefab::CriteriaEvaluator.new(config, project_env_id: PROJECT_ENV_ID, resolver: nil, base_client: FakeBaseClient.new,
163
162
  namespace: nil)
164
163
 
165
164
  assert_equal DESIRED_VALUE, evaluator.evaluate(context({})).string
@@ -168,29 +167,29 @@ class TestCriteriaEvaluator < Minitest::Test
168
167
  end
169
168
 
170
169
  def test_prop_ends_with_one_of
171
- config = Prefab::Config.new(
170
+ config = PrefabProto::Config.new(
172
171
  key: KEY,
173
172
  rows: [
174
173
  DEFAULT_ROW,
175
- Prefab::ConfigRow.new(
174
+ PrefabProto::ConfigRow.new(
176
175
  project_env_id: PROJECT_ENV_ID,
177
176
  values: [
178
- Prefab::ConditionalValue.new(
177
+ PrefabProto::ConditionalValue.new(
179
178
  criteria: [
180
- Prefab::Criterion.new(
181
- operator: Prefab::Criterion::CriterionOperator::PROP_ENDS_WITH_ONE_OF,
179
+ PrefabProto::Criterion.new(
180
+ operator: PrefabProto::Criterion::CriterionOperator::PROP_ENDS_WITH_ONE_OF,
182
181
  value_to_match: string_list(['hotmail.com', 'gmail.com']),
183
182
  property_name: 'user.email'
184
183
  )
185
184
  ],
186
- value: Prefab::ConfigValue.new(string: DESIRED_VALUE)
185
+ value: PrefabProto::ConfigValue.new(string: DESIRED_VALUE)
187
186
  )
188
187
  ]
189
188
  )
190
189
  ]
191
190
  )
192
191
 
193
- evaluator = Prefab::CriteriaEvaluator.new(config, project_env_id: PROJECT_ENV_ID, resolver: nil, base_client: nil,
192
+ evaluator = Prefab::CriteriaEvaluator.new(config, project_env_id: PROJECT_ENV_ID, resolver: nil, base_client: FakeBaseClient.new,
194
193
  namespace: nil)
195
194
 
196
195
  assert_equal DEFAULT_VALUE, evaluator.evaluate(context({})).string
@@ -199,29 +198,29 @@ class TestCriteriaEvaluator < Minitest::Test
199
198
  end
200
199
 
201
200
  def test_prop_does_not_end_with_one_of
202
- config = Prefab::Config.new(
201
+ config = PrefabProto::Config.new(
203
202
  key: KEY,
204
203
  rows: [
205
204
  DEFAULT_ROW,
206
- Prefab::ConfigRow.new(
205
+ PrefabProto::ConfigRow.new(
207
206
  project_env_id: PROJECT_ENV_ID,
208
207
  values: [
209
- Prefab::ConditionalValue.new(
208
+ PrefabProto::ConditionalValue.new(
210
209
  criteria: [
211
- Prefab::Criterion.new(
212
- operator: Prefab::Criterion::CriterionOperator::PROP_DOES_NOT_END_WITH_ONE_OF,
210
+ PrefabProto::Criterion.new(
211
+ operator: PrefabProto::Criterion::CriterionOperator::PROP_DOES_NOT_END_WITH_ONE_OF,
213
212
  value_to_match: string_list(['hotmail.com', 'gmail.com']),
214
213
  property_name: 'user.email'
215
214
  )
216
215
  ],
217
- value: Prefab::ConfigValue.new(string: DESIRED_VALUE)
216
+ value: PrefabProto::ConfigValue.new(string: DESIRED_VALUE)
218
217
  )
219
218
  ]
220
219
  )
221
220
  ]
222
221
  )
223
222
 
224
- evaluator = Prefab::CriteriaEvaluator.new(config, project_env_id: PROJECT_ENV_ID, resolver: nil, base_client: nil,
223
+ evaluator = Prefab::CriteriaEvaluator.new(config, project_env_id: PROJECT_ENV_ID, resolver: nil, base_client: FakeBaseClient.new,
225
224
  namespace: nil)
226
225
 
227
226
  assert_equal DESIRED_VALUE, evaluator.evaluate(context({})).string
@@ -232,63 +231,63 @@ class TestCriteriaEvaluator < Minitest::Test
232
231
  def test_in_seg
233
232
  segment_key = 'segment_key'
234
233
 
235
- segment_config = Prefab::Config.new(
236
- config_type: Prefab::ConfigType::SEGMENT,
234
+ segment_config = PrefabProto::Config.new(
235
+ config_type: PrefabProto::ConfigType::SEGMENT,
237
236
  key: segment_key,
238
237
  rows: [
239
- Prefab::ConfigRow.new(
238
+ PrefabProto::ConfigRow.new(
240
239
  values: [
241
- Prefab::ConditionalValue.new(
242
- value: Prefab::ConfigValue.new(bool: true),
240
+ PrefabProto::ConditionalValue.new(
241
+ value: PrefabProto::ConfigValue.new(bool: true),
243
242
  criteria: [
244
- Prefab::Criterion.new(
245
- operator: Prefab::Criterion::CriterionOperator::PROP_ENDS_WITH_ONE_OF,
243
+ PrefabProto::Criterion.new(
244
+ operator: PrefabProto::Criterion::CriterionOperator::PROP_ENDS_WITH_ONE_OF,
246
245
  value_to_match: string_list(['hotmail.com', 'gmail.com']),
247
246
  property_name: 'user.email'
248
247
  )
249
248
  ]
250
249
  ),
251
- Prefab::ConditionalValue.new(
252
- value: Prefab::ConfigValue.new(bool: false)
250
+ PrefabProto::ConditionalValue.new(
251
+ value: PrefabProto::ConfigValue.new(bool: false)
253
252
  )
254
253
  ]
255
254
  )
256
255
  ]
257
256
  )
258
257
 
259
- config = Prefab::Config.new(
258
+ config = PrefabProto::Config.new(
260
259
  key: KEY,
261
260
  rows: [
262
261
  DEFAULT_ROW,
263
262
 
264
263
  # wrong env
265
- Prefab::ConfigRow.new(
264
+ PrefabProto::ConfigRow.new(
266
265
  project_env_id: TEST_ENV_ID,
267
266
  values: [
268
- Prefab::ConditionalValue.new(
267
+ PrefabProto::ConditionalValue.new(
269
268
  criteria: [
270
- Prefab::Criterion.new(
271
- operator: Prefab::Criterion::CriterionOperator::IN_SEG,
272
- value_to_match: Prefab::ConfigValue.new(string: segment_key)
269
+ PrefabProto::Criterion.new(
270
+ operator: PrefabProto::Criterion::CriterionOperator::IN_SEG,
271
+ value_to_match: PrefabProto::ConfigValue.new(string: segment_key)
273
272
  )
274
273
  ],
275
- value: Prefab::ConfigValue.new(string: WRONG_ENV_VALUE)
274
+ value: PrefabProto::ConfigValue.new(string: WRONG_ENV_VALUE)
276
275
  )
277
276
  ]
278
277
  ),
279
278
 
280
279
  # correct env
281
- Prefab::ConfigRow.new(
280
+ PrefabProto::ConfigRow.new(
282
281
  project_env_id: PROJECT_ENV_ID,
283
282
  values: [
284
- Prefab::ConditionalValue.new(
283
+ PrefabProto::ConditionalValue.new(
285
284
  criteria: [
286
- Prefab::Criterion.new(
287
- operator: Prefab::Criterion::CriterionOperator::IN_SEG,
288
- value_to_match: Prefab::ConfigValue.new(string: segment_key)
285
+ PrefabProto::Criterion.new(
286
+ operator: PrefabProto::Criterion::CriterionOperator::IN_SEG,
287
+ value_to_match: PrefabProto::ConfigValue.new(string: segment_key)
289
288
  )
290
289
  ],
291
- value: Prefab::ConfigValue.new(string: DESIRED_VALUE)
290
+ value: PrefabProto::ConfigValue.new(string: DESIRED_VALUE)
292
291
  )
293
292
  ]
294
293
  )
@@ -296,7 +295,7 @@ class TestCriteriaEvaluator < Minitest::Test
296
295
  )
297
296
 
298
297
  evaluator = Prefab::CriteriaEvaluator.new(config, project_env_id: PROJECT_ENV_ID,
299
- base_client: nil, namespace: nil,
298
+ base_client: FakeBaseClient.new, namespace: nil,
300
299
  resolver: resolver_fake({ segment_key => segment_config }))
301
300
 
302
301
  assert_equal DEFAULT_VALUE, evaluator.evaluate(context({})).string
@@ -307,45 +306,45 @@ class TestCriteriaEvaluator < Minitest::Test
307
306
  def test_not_in_seg
308
307
  segment_key = 'segment_key'
309
308
 
310
- segment_config = Prefab::Config.new(
311
- config_type: Prefab::ConfigType::SEGMENT,
309
+ segment_config = PrefabProto::Config.new(
310
+ config_type: PrefabProto::ConfigType::SEGMENT,
312
311
  key: segment_key,
313
312
  rows: [
314
- Prefab::ConfigRow.new(
313
+ PrefabProto::ConfigRow.new(
315
314
  values: [
316
- Prefab::ConditionalValue.new(
317
- value: Prefab::ConfigValue.new(bool: true),
315
+ PrefabProto::ConditionalValue.new(
316
+ value: PrefabProto::ConfigValue.new(bool: true),
318
317
  criteria: [
319
- Prefab::Criterion.new(
320
- operator: Prefab::Criterion::CriterionOperator::PROP_ENDS_WITH_ONE_OF,
318
+ PrefabProto::Criterion.new(
319
+ operator: PrefabProto::Criterion::CriterionOperator::PROP_ENDS_WITH_ONE_OF,
321
320
  value_to_match: string_list(['hotmail.com', 'gmail.com']),
322
321
  property_name: 'user.email'
323
322
  )
324
323
  ]
325
324
  ),
326
- Prefab::ConditionalValue.new(
327
- value: Prefab::ConfigValue.new(bool: false)
325
+ PrefabProto::ConditionalValue.new(
326
+ value: PrefabProto::ConfigValue.new(bool: false)
328
327
  )
329
328
  ]
330
329
  )
331
330
  ]
332
331
  )
333
332
 
334
- config = Prefab::Config.new(
333
+ config = PrefabProto::Config.new(
335
334
  key: KEY,
336
335
  rows: [
337
336
  DEFAULT_ROW,
338
- Prefab::ConfigRow.new(
337
+ PrefabProto::ConfigRow.new(
339
338
  project_env_id: PROJECT_ENV_ID,
340
339
  values: [
341
- Prefab::ConditionalValue.new(
340
+ PrefabProto::ConditionalValue.new(
342
341
  criteria: [
343
- Prefab::Criterion.new(
344
- operator: Prefab::Criterion::CriterionOperator::NOT_IN_SEG,
345
- value_to_match: Prefab::ConfigValue.new(string: segment_key)
342
+ PrefabProto::Criterion.new(
343
+ operator: PrefabProto::Criterion::CriterionOperator::NOT_IN_SEG,
344
+ value_to_match: PrefabProto::ConfigValue.new(string: segment_key)
346
345
  )
347
346
  ],
348
- value: Prefab::ConfigValue.new(string: DESIRED_VALUE)
347
+ value: PrefabProto::ConfigValue.new(string: DESIRED_VALUE)
349
348
  )
350
349
  ]
351
350
  )
@@ -353,7 +352,7 @@ class TestCriteriaEvaluator < Minitest::Test
353
352
  )
354
353
 
355
354
  evaluator = Prefab::CriteriaEvaluator.new(config, project_env_id: PROJECT_ENV_ID,
356
- base_client: nil, namespace: nil,
355
+ base_client: FakeBaseClient.new, namespace: nil,
357
356
  resolver: resolver_fake({ segment_key => segment_config }))
358
357
 
359
358
  assert_equal DESIRED_VALUE, evaluator.evaluate(context({})).string
@@ -364,57 +363,57 @@ class TestCriteriaEvaluator < Minitest::Test
364
363
  def test_multiple_conditions_in_one_value
365
364
  segment_key = 'segment_key'
366
365
 
367
- segment_config = Prefab::Config.new(
368
- config_type: Prefab::ConfigType::SEGMENT,
366
+ segment_config = PrefabProto::Config.new(
367
+ config_type: PrefabProto::ConfigType::SEGMENT,
369
368
  key: segment_key,
370
369
  rows: [
371
- Prefab::ConfigRow.new(
370
+ PrefabProto::ConfigRow.new(
372
371
  values: [
373
- Prefab::ConditionalValue.new(
374
- value: Prefab::ConfigValue.new(bool: true),
372
+ PrefabProto::ConditionalValue.new(
373
+ value: PrefabProto::ConfigValue.new(bool: true),
375
374
  criteria: [
376
- Prefab::Criterion.new(
377
- operator: Prefab::Criterion::CriterionOperator::PROP_ENDS_WITH_ONE_OF,
375
+ PrefabProto::Criterion.new(
376
+ operator: PrefabProto::Criterion::CriterionOperator::PROP_ENDS_WITH_ONE_OF,
378
377
  value_to_match: string_list(['prefab.cloud', 'gmail.com']),
379
378
  property_name: 'user.email'
380
379
  ),
381
380
 
382
- Prefab::Criterion.new(
383
- operator: Prefab::Criterion::CriterionOperator::PROP_IS_ONE_OF,
384
- value_to_match: Prefab::ConfigValue.new(bool: true),
381
+ PrefabProto::Criterion.new(
382
+ operator: PrefabProto::Criterion::CriterionOperator::PROP_IS_ONE_OF,
383
+ value_to_match: PrefabProto::ConfigValue.new(bool: true),
385
384
  property_name: 'user.admin'
386
385
  )
387
386
  ]
388
387
  ),
389
- Prefab::ConditionalValue.new(
390
- value: Prefab::ConfigValue.new(bool: false)
388
+ PrefabProto::ConditionalValue.new(
389
+ value: PrefabProto::ConfigValue.new(bool: false)
391
390
  )
392
391
  ]
393
392
  )
394
393
  ]
395
394
  )
396
395
 
397
- config = Prefab::Config.new(
396
+ config = PrefabProto::Config.new(
398
397
  key: KEY,
399
398
  rows: [
400
399
  DEFAULT_ROW,
401
- Prefab::ConfigRow.new(
400
+ PrefabProto::ConfigRow.new(
402
401
  project_env_id: PROJECT_ENV_ID,
403
402
  values: [
404
- Prefab::ConditionalValue.new(
403
+ PrefabProto::ConditionalValue.new(
405
404
  criteria: [
406
- Prefab::Criterion.new(
407
- operator: Prefab::Criterion::CriterionOperator::IN_SEG,
408
- value_to_match: Prefab::ConfigValue.new(string: segment_key)
405
+ PrefabProto::Criterion.new(
406
+ operator: PrefabProto::Criterion::CriterionOperator::IN_SEG,
407
+ value_to_match: PrefabProto::ConfigValue.new(string: segment_key)
409
408
  ),
410
409
 
411
- Prefab::Criterion.new(
412
- operator: Prefab::Criterion::CriterionOperator::PROP_IS_NOT_ONE_OF,
413
- value_to_match: Prefab::ConfigValue.new(bool: true),
410
+ PrefabProto::Criterion.new(
411
+ operator: PrefabProto::Criterion::CriterionOperator::PROP_IS_NOT_ONE_OF,
412
+ value_to_match: PrefabProto::ConfigValue.new(bool: true),
414
413
  property_name: 'user.deleted'
415
414
  )
416
415
  ],
417
- value: Prefab::ConfigValue.new(string: DESIRED_VALUE)
416
+ value: PrefabProto::ConfigValue.new(string: DESIRED_VALUE)
418
417
  )
419
418
  ]
420
419
  )
@@ -422,7 +421,7 @@ class TestCriteriaEvaluator < Minitest::Test
422
421
  )
423
422
 
424
423
  evaluator = Prefab::CriteriaEvaluator.new(config, project_env_id: PROJECT_ENV_ID,
425
- base_client: nil, namespace: nil,
424
+ base_client: FakeBaseClient.new, namespace: nil,
426
425
  resolver: resolver_fake({ segment_key => segment_config }))
427
426
 
428
427
  assert_equal DEFAULT_VALUE, evaluator.evaluate(context({})).string
@@ -439,61 +438,61 @@ class TestCriteriaEvaluator < Minitest::Test
439
438
  def test_multiple_conditions_in_multiple_values
440
439
  segment_key = 'segment_key'
441
440
 
442
- segment_config = Prefab::Config.new(
443
- config_type: Prefab::ConfigType::SEGMENT,
441
+ segment_config = PrefabProto::Config.new(
442
+ config_type: PrefabProto::ConfigType::SEGMENT,
444
443
  key: segment_key,
445
444
  rows: [
446
- Prefab::ConfigRow.new(
445
+ PrefabProto::ConfigRow.new(
447
446
  values: [
448
- Prefab::ConditionalValue.new(
449
- value: Prefab::ConfigValue.new(bool: true),
447
+ PrefabProto::ConditionalValue.new(
448
+ value: PrefabProto::ConfigValue.new(bool: true),
450
449
  criteria: [
451
- Prefab::Criterion.new(
452
- operator: Prefab::Criterion::CriterionOperator::PROP_ENDS_WITH_ONE_OF,
450
+ PrefabProto::Criterion.new(
451
+ operator: PrefabProto::Criterion::CriterionOperator::PROP_ENDS_WITH_ONE_OF,
453
452
  value_to_match: string_list(['prefab.cloud', 'gmail.com']),
454
453
  property_name: 'user.email'
455
454
  )
456
455
  ]
457
456
  ),
458
- Prefab::ConditionalValue.new(
459
- value: Prefab::ConfigValue.new(bool: true),
457
+ PrefabProto::ConditionalValue.new(
458
+ value: PrefabProto::ConfigValue.new(bool: true),
460
459
  criteria: [
461
- Prefab::Criterion.new(
462
- operator: Prefab::Criterion::CriterionOperator::PROP_IS_ONE_OF,
463
- value_to_match: Prefab::ConfigValue.new(bool: true),
460
+ PrefabProto::Criterion.new(
461
+ operator: PrefabProto::Criterion::CriterionOperator::PROP_IS_ONE_OF,
462
+ value_to_match: PrefabProto::ConfigValue.new(bool: true),
464
463
  property_name: 'user.admin'
465
464
  )
466
465
  ]
467
466
  ),
468
- Prefab::ConditionalValue.new(
469
- value: Prefab::ConfigValue.new(bool: false)
467
+ PrefabProto::ConditionalValue.new(
468
+ value: PrefabProto::ConfigValue.new(bool: false)
470
469
  )
471
470
  ]
472
471
  )
473
472
  ]
474
473
  )
475
474
 
476
- config = Prefab::Config.new(
475
+ config = PrefabProto::Config.new(
477
476
  key: KEY,
478
477
  rows: [
479
478
  DEFAULT_ROW,
480
- Prefab::ConfigRow.new(
479
+ PrefabProto::ConfigRow.new(
481
480
  project_env_id: PROJECT_ENV_ID,
482
481
  values: [
483
- Prefab::ConditionalValue.new(
482
+ PrefabProto::ConditionalValue.new(
484
483
  criteria: [
485
- Prefab::Criterion.new(
486
- operator: Prefab::Criterion::CriterionOperator::IN_SEG,
487
- value_to_match: Prefab::ConfigValue.new(string: segment_key)
484
+ PrefabProto::Criterion.new(
485
+ operator: PrefabProto::Criterion::CriterionOperator::IN_SEG,
486
+ value_to_match: PrefabProto::ConfigValue.new(string: segment_key)
488
487
  ),
489
488
 
490
- Prefab::Criterion.new(
491
- operator: Prefab::Criterion::CriterionOperator::PROP_IS_NOT_ONE_OF,
492
- value_to_match: Prefab::ConfigValue.new(bool: true),
489
+ PrefabProto::Criterion.new(
490
+ operator: PrefabProto::Criterion::CriterionOperator::PROP_IS_NOT_ONE_OF,
491
+ value_to_match: PrefabProto::ConfigValue.new(bool: true),
493
492
  property_name: 'user.deleted'
494
493
  )
495
494
  ],
496
- value: Prefab::ConfigValue.new(string: DESIRED_VALUE)
495
+ value: PrefabProto::ConfigValue.new(string: DESIRED_VALUE)
497
496
  )
498
497
  ]
499
498
  )
@@ -501,7 +500,7 @@ class TestCriteriaEvaluator < Minitest::Test
501
500
  )
502
501
 
503
502
  evaluator = Prefab::CriteriaEvaluator.new(config, project_env_id: PROJECT_ENV_ID,
504
- base_client: nil, namespace: nil,
503
+ base_client: FakeBaseClient.new, namespace: nil,
505
504
  resolver: resolver_fake({ segment_key => segment_config }))
506
505
 
507
506
  assert_equal DEFAULT_VALUE, evaluator.evaluate(context({})).string
@@ -517,22 +516,22 @@ class TestCriteriaEvaluator < Minitest::Test
517
516
  end
518
517
 
519
518
  def test_stringifying_property_values_and_names
520
- config = Prefab::Config.new(
519
+ config = PrefabProto::Config.new(
521
520
  key: KEY,
522
521
  rows: [
523
522
  DEFAULT_ROW,
524
- Prefab::ConfigRow.new(
523
+ PrefabProto::ConfigRow.new(
525
524
  project_env_id: PROJECT_ENV_ID,
526
525
  values: [
527
- Prefab::ConditionalValue.new(
526
+ PrefabProto::ConditionalValue.new(
528
527
  criteria: [
529
- Prefab::Criterion.new(
530
- operator: Prefab::Criterion::CriterionOperator::PROP_IS_ONE_OF,
528
+ PrefabProto::Criterion.new(
529
+ operator: PrefabProto::Criterion::CriterionOperator::PROP_IS_ONE_OF,
531
530
  value_to_match: string_list(%w[1 true hello]),
532
531
  property_name: 'team.name'
533
532
  )
534
533
  ],
535
- value: Prefab::ConfigValue.new(string: DESIRED_VALUE)
534
+ value: PrefabProto::ConfigValue.new(string: DESIRED_VALUE)
536
535
  )
537
536
  ]
538
537
  )
@@ -540,7 +539,7 @@ class TestCriteriaEvaluator < Minitest::Test
540
539
  )
541
540
 
542
541
  evaluator = Prefab::CriteriaEvaluator.new(config, project_env_id: PROJECT_ENV_ID, resolver: nil,
543
- namespace: nil, base_client: nil)
542
+ namespace: nil, base_client: FakeBaseClient.new)
544
543
 
545
544
  assert_equal DEFAULT_VALUE, evaluator.evaluate(context({})).string
546
545
  assert_equal DEFAULT_VALUE, evaluator.evaluate(context(team: { name: 'prefab.cloud' })).string
@@ -553,10 +552,101 @@ class TestCriteriaEvaluator < Minitest::Test
553
552
  end
554
553
  end
555
554
 
555
+ def test_in_int_range
556
+ config = PrefabProto::Config.new(
557
+ key: KEY,
558
+ rows: [
559
+ PrefabProto::ConfigRow.new(
560
+ project_env_id: PROJECT_ENV_ID,
561
+ values: [
562
+ PrefabProto::ConditionalValue.new(
563
+ criteria: [
564
+ PrefabProto::Criterion.new(operator: PrefabProto::Criterion::CriterionOperator::IN_INT_RANGE,
565
+ value_to_match: PrefabProto::ConfigValue.new(int_range: PrefabProto::IntRange.new(start: 30, end: 40)), property_name: 'user.age')
566
+ ],
567
+ value: PrefabProto::ConfigValue.new(string: DESIRED_VALUE)
568
+ ),
569
+
570
+ PrefabProto::ConditionalValue.new(
571
+ criteria: [
572
+ PrefabProto::Criterion.new(operator: PrefabProto::Criterion::CriterionOperator::ALWAYS_TRUE)
573
+ ],
574
+ value: PrefabProto::ConfigValue.new(string: DEFAULT_VALUE)
575
+ )
576
+ ]
577
+ )
578
+ ]
579
+ )
580
+
581
+ evaluator = Prefab::CriteriaEvaluator.new(config, project_env_id: PROJECT_ENV_ID, resolver: nil,
582
+ namespace: nil, base_client: FakeBaseClient.new)
583
+
584
+ assert_equal DEFAULT_VALUE, evaluator.evaluate(context({})).string
585
+ assert_equal DESIRED_VALUE, evaluator.evaluate(context({ 'user' => { 'age' => 32 } })).string
586
+ assert_equal DEFAULT_VALUE, evaluator.evaluate(context({ 'user' => { 'age' => 29 } })).string
587
+ assert_equal DEFAULT_VALUE, evaluator.evaluate(context({ 'user' => { 'age' => 41 } })).string
588
+ end
589
+
590
+ def test_in_int_range_for_time
591
+ now = Time.now
592
+
593
+ config = PrefabProto::Config.new(
594
+ key: KEY,
595
+ rows: [
596
+ PrefabProto::ConfigRow.new(
597
+ project_env_id: PROJECT_ENV_ID,
598
+ values: [
599
+ PrefabProto::ConditionalValue.new(
600
+ criteria: [
601
+ PrefabProto::Criterion.new(operator: PrefabProto::Criterion::CriterionOperator::IN_INT_RANGE,
602
+ value_to_match: PrefabProto::ConfigValue.new(
603
+ int_range: PrefabProto::IntRange.new(
604
+ start: (now.to_i - 60) * 1000, end: (now.to_i + 60) * 1000
605
+ )
606
+ ), property_name: 'prefab.current-time')
607
+ ],
608
+ value: PrefabProto::ConfigValue.new(string: DESIRED_VALUE)
609
+ ),
610
+
611
+ PrefabProto::ConditionalValue.new(
612
+ criteria: [
613
+ PrefabProto::Criterion.new(operator: PrefabProto::Criterion::CriterionOperator::ALWAYS_TRUE)
614
+ ],
615
+ value: PrefabProto::ConfigValue.new(string: DEFAULT_VALUE)
616
+ )
617
+ ]
618
+ )
619
+ ]
620
+ )
621
+
622
+ evaluator = Prefab::CriteriaEvaluator.new(config, project_env_id: PROJECT_ENV_ID, resolver: nil,
623
+ namespace: nil, base_client: FakeBaseClient.new)
624
+
625
+ Timecop.freeze(now) do
626
+ assert_equal DESIRED_VALUE, evaluator.evaluate(context({})).string
627
+ end
628
+
629
+ Timecop.freeze(now - 60) do
630
+ assert_equal DESIRED_VALUE, evaluator.evaluate(context({})).string
631
+ end
632
+
633
+ Timecop.freeze(now - 61) do
634
+ assert_equal DEFAULT_VALUE, evaluator.evaluate(context({})).string
635
+ end
636
+
637
+ Timecop.freeze(now + 59) do
638
+ assert_equal DESIRED_VALUE, evaluator.evaluate(context({})).string
639
+ end
640
+
641
+ Timecop.freeze(now + 60) do
642
+ assert_equal DEFAULT_VALUE, evaluator.evaluate(context({})).string
643
+ end
644
+ end
645
+
556
646
  private
557
647
 
558
648
  def string_list(values)
559
- Prefab::ConfigValue.new(string_list: Prefab::StringList.new(values: values))
649
+ PrefabProto::ConfigValue.new(string_list: PrefabProto::StringList.new(values: values))
560
650
  end
561
651
 
562
652
  class FakeResolver
@@ -571,7 +661,7 @@ class TestCriteriaEvaluator < Minitest::Test
571
661
  def get(key, properties = {})
572
662
  # This only gets called for segments, so we don't need to pass in a resolver
573
663
  Prefab::CriteriaEvaluator.new(@config[key], project_env_id: nil, resolver: nil,
574
- namespace: nil, base_client: nil).evaluate(properties)
664
+ namespace: nil, base_client: FakeBaseClient.new).evaluate(properties)
575
665
  end
576
666
  end
577
667
 
@@ -582,4 +672,17 @@ class TestCriteriaEvaluator < Minitest::Test
582
672
  def context(properties)
583
673
  Prefab::Context.new(properties)
584
674
  end
675
+
676
+ class FakeLogger
677
+ def info(msg)
678
+ # loudly complain about unexpected log messages
679
+ raise msg
680
+ end
681
+ end
682
+
683
+ class FakeBaseClient
684
+ def log
685
+ FakeLogger.new
686
+ end
687
+ end
585
688
  end