99from .types import LocalFlagsConfig , ExperimentationFlag , RuleSet , Variant , Rollout , FlagTestUsers , ExperimentationFlags , VariantOverride , SelectedVariant
1010from .local_feature_flags import LocalFeatureFlagsProvider
1111
12+ TEST_FLAG_KEY = "test_flag"
1213
1314def create_test_flag (
14- flag_key : str = "test_flag" ,
15+ flag_key : str = TEST_FLAG_KEY ,
1516 context : str = "distinct_id" ,
1617 variants : Optional [list [Variant ]] = None ,
1718 variant_override : Optional [VariantOverride ] = None ,
1819 rollout_percentage : float = 100.0 ,
19- runtime_evaluation : Optional [Dict ] = None ,
20+ runtime_evaluation_legacy_definition : Optional [Dict ] = None ,
21+ runtime_evaluation_rule : Optional [Dict ] = None ,
2022 test_users : Optional [Dict [str , str ]] = None ,
2123 experiment_id : Optional [str ] = None ,
2224 is_experiment_active : Optional [bool ] = None ,
@@ -30,7 +32,8 @@ def create_test_flag(
3032
3133 rollouts = [Rollout (
3234 rollout_percentage = rollout_percentage ,
33- runtime_evaluation_definition = runtime_evaluation ,
35+ runtime_evaluation_definition = runtime_evaluation_legacy_definition ,
36+ runtime_evaluation_rule = runtime_evaluation_rule ,
3437 variant_override = variant_override ,
3538 variant_splits = variant_splits
3639 )]
@@ -127,14 +130,14 @@ async def test_get_variant_value_returns_fallback_when_flag_does_not_exist(self)
127130 async def test_get_variant_value_returns_fallback_when_no_context (self ):
128131 flag = create_test_flag (context = "distinct_id" )
129132 await self .setup_flags ([flag ])
130- result = self ._flags .get_variant_value ("test_flag" , "fallback" , {})
133+ result = self ._flags .get_variant_value (TEST_FLAG_KEY , "fallback" , {})
131134 assert result == "fallback"
132135
133136 @respx .mock
134137 async def test_get_variant_value_returns_fallback_when_wrong_context_key (self ):
135138 flag = create_test_flag (context = "user_id" )
136139 await self .setup_flags ([flag ])
137- result = self ._flags .get_variant_value ("test_flag" , "fallback" , {"distinct_id" : "user123" })
140+ result = self ._flags .get_variant_value (TEST_FLAG_KEY , "fallback" , {"distinct_id" : "user123" })
138141 assert result == "fallback"
139142
140143 @respx .mock
@@ -149,7 +152,7 @@ async def test_get_variant_value_returns_test_user_variant_when_configured(self)
149152 )
150153
151154 await self .setup_flags ([flag ])
152- result = self ._flags .get_variant_value ("test_flag" , "control" , {"distinct_id" : "test_user" })
155+ result = self ._flags .get_variant_value (TEST_FLAG_KEY , "control" , {"distinct_id" : "test_user" })
153156 assert result == "true"
154157
155158 @respx .mock
@@ -165,27 +168,59 @@ async def test_get_variant_value_returns_fallback_when_test_user_variant_not_con
165168 await self .setup_flags ([flag ])
166169 with patch ('mixpanel.flags.utils.normalized_hash' ) as mock_hash :
167170 mock_hash .return_value = 0.5
168- result = self ._flags .get_variant_value ("test_flag" , "fallback" , {"distinct_id" : "test_user" })
171+ result = self ._flags .get_variant_value (TEST_FLAG_KEY , "fallback" , {"distinct_id" : "test_user" })
169172 assert result == "false"
170173
171174 @respx .mock
172175 async def test_get_variant_value_returns_fallback_when_rollout_percentage_zero (self ):
173176 flag = create_test_flag (rollout_percentage = 0.0 )
174177 await self .setup_flags ([flag ])
175- result = self ._flags .get_variant_value ("test_flag" , "fallback" , {"distinct_id" : "user123" })
178+ result = self ._flags .get_variant_value (TEST_FLAG_KEY , "fallback" , {"distinct_id" : "user123" })
176179 assert result == "fallback"
177180
178181 @respx .mock
179182 async def test_get_variant_value_returns_variant_when_rollout_percentage_hundred (self ):
180183 flag = create_test_flag (rollout_percentage = 100.0 )
181184 await self .setup_flags ([flag ])
182- result = self ._flags .get_variant_value ("test_flag" , "fallback" , {"distinct_id" : "user123" })
185+ result = self ._flags .get_variant_value (TEST_FLAG_KEY , "fallback" , {"distinct_id" : "user123" })
183186 assert result != "fallback"
184187
188+ # TODO Joshua start here
189+ # TODO problem test doesn't fail
190+ @respx .mock
191+ async def test_get_variant_value_respects_runtime_evaluation_rule_satisfied (self ):
192+ runtime_eval = {"oops" : "sorry" }
193+ flag = create_test_flag (runtime_evaluation_rule = runtime_eval )
194+ await self .setup_flags ([flag ])
195+ context = {
196+ "distinct_id" : "user123" ,
197+ "custom_properties" : {
198+ "plan" : "premium" ,
199+ "region" : "US"
200+ }
201+ }
202+ result = self ._flags .get_variant_value (TEST_FLAG_KEY , "fallback" , context )
203+ assert result != "fallback"
204+
205+ @respx .mock
206+ async def test_get_variant_value_respects_runtime_evaluation_rule_not_satisfied (self ):
207+ runtime_eval = {"oops" : "sorry" }
208+ flag = create_test_flag (runtime_evaluation_rule = runtime_eval )
209+ await self .setup_flags ([flag ])
210+ context = {
211+ "distinct_id" : "user123" ,
212+ "custom_properties" : {
213+ "plan" : "premium" ,
214+ "region" : "US"
215+ }
216+ }
217+ result = self ._flags .get_variant_value (TEST_FLAG_KEY , "fallback" , context )
218+ assert result == "fallback"
219+
185220 @respx .mock
186221 async def test_get_variant_value_respects_runtime_evaluation_satisfied (self ):
187222 runtime_eval = {"plan" : "premium" , "region" : "US" }
188- flag = create_test_flag (runtime_evaluation = runtime_eval )
223+ flag = create_test_flag (runtime_evaluation_legacy_definition = runtime_eval )
189224 await self .setup_flags ([flag ])
190225 context = {
191226 "distinct_id" : "user123" ,
@@ -194,13 +229,13 @@ async def test_get_variant_value_respects_runtime_evaluation_satisfied(self):
194229 "region" : "US"
195230 }
196231 }
197- result = self ._flags .get_variant_value ("test_flag" , "fallback" , context )
232+ result = self ._flags .get_variant_value (TEST_FLAG_KEY , "fallback" , context )
198233 assert result != "fallback"
199234
200235 @respx .mock
201236 async def test_get_variant_value_returns_fallback_when_runtime_evaluation_not_satisfied (self ):
202237 runtime_eval = {"plan" : "premium" , "region" : "US" }
203- flag = create_test_flag (runtime_evaluation = runtime_eval )
238+ flag = create_test_flag (runtime_evaluation_legacy_definition = runtime_eval )
204239 await self .setup_flags ([flag ])
205240 context = {
206241 "distinct_id" : "user123" ,
@@ -209,7 +244,7 @@ async def test_get_variant_value_returns_fallback_when_runtime_evaluation_not_sa
209244 "region" : "US"
210245 }
211246 }
212- result = self ._flags .get_variant_value ("test_flag" , "fallback" , context )
247+ result = self ._flags .get_variant_value (TEST_FLAG_KEY , "fallback" , context )
213248 assert result == "fallback"
214249
215250 @respx .mock
@@ -221,7 +256,7 @@ async def test_get_variant_value_picks_correct_variant_with_hundred_percent_spli
221256 ]
222257 flag = create_test_flag (variants = variants , rollout_percentage = 100.0 )
223258 await self .setup_flags ([flag ])
224- result = self ._flags .get_variant_value ("test_flag" , "fallback" , {"distinct_id" : "user123" })
259+ result = self ._flags .get_variant_value (TEST_FLAG_KEY , "fallback" , {"distinct_id" : "user123" })
225260 assert result == "variant_a"
226261
227262 @respx .mock
@@ -234,7 +269,7 @@ async def test_get_variant_value_picks_correct_variant_with_half_migrated_group_
234269 variant_splits = {"A" : 0.0 , "B" : 100.0 , "C" : 0.0 }
235270 flag = create_test_flag (variants = variants , rollout_percentage = 100.0 , variant_splits = variant_splits )
236271 await self .setup_flags ([flag ])
237- result = self ._flags .get_variant_value ("test_flag" , "fallback" , {"distinct_id" : "user123" })
272+ result = self ._flags .get_variant_value (TEST_FLAG_KEY , "fallback" , {"distinct_id" : "user123" })
238273 assert result == "variant_b"
239274
240275 @respx .mock
@@ -247,7 +282,7 @@ async def test_get_variant_value_picks_correct_variant_with_full_migrated_group_
247282 variant_splits = {"A" : 0.0 , "B" : 0.0 , "C" : 100.0 }
248283 flag = create_test_flag (variants = variants , rollout_percentage = 100.0 , variant_splits = variant_splits )
249284 await self .setup_flags ([flag ])
250- result = self ._flags .get_variant_value ("test_flag" , "fallback" , {"distinct_id" : "user123" })
285+ result = self ._flags .get_variant_value (TEST_FLAG_KEY , "fallback" , {"distinct_id" : "user123" })
251286 assert result == "variant_c"
252287
253288 @respx .mock
@@ -258,7 +293,7 @@ async def test_get_variant_value_picks_overriden_variant(self):
258293 ]
259294 flag = create_test_flag (variants = variants , variant_override = VariantOverride (key = "B" ))
260295 await self .setup_flags ([flag ])
261- result = self ._flags .get_variant_value ("test_flag" , "control" , {"distinct_id" : "user123" })
296+ result = self ._flags .get_variant_value (TEST_FLAG_KEY , "control" , {"distinct_id" : "user123" })
262297 assert result == "variant_b"
263298
264299 @respx .mock
@@ -267,7 +302,7 @@ async def test_get_variant_value_tracks_exposure_when_variant_selected(self):
267302 await self .setup_flags ([flag ])
268303 with patch ('mixpanel.flags.utils.normalized_hash' ) as mock_hash :
269304 mock_hash .return_value = 0.5
270- _ = self ._flags .get_variant_value ("test_flag" , "fallback" , {"distinct_id" : "user123" })
305+ _ = self ._flags .get_variant_value (TEST_FLAG_KEY , "fallback" , {"distinct_id" : "user123" })
271306 self ._mock_tracker .assert_called_once ()
272307
273308 @respx .mock
@@ -292,7 +327,7 @@ async def test_get_variant_value_tracks_exposure_with_correct_properties(self, e
292327
293328 with patch ('mixpanel.flags.utils.normalized_hash' ) as mock_hash :
294329 mock_hash .return_value = 0.5
295- _ = self ._flags .get_variant_value ("test_flag" , "fallback" , {"distinct_id" : distinct_id })
330+ _ = self ._flags .get_variant_value (TEST_FLAG_KEY , "fallback" , {"distinct_id" : distinct_id })
296331
297332 self ._mock_tracker .assert_called_once ()
298333
@@ -364,7 +399,7 @@ async def test_track_exposure_event_successfully_tracks(self):
364399 await self .setup_flags ([flag ])
365400
366401 variant = SelectedVariant (key = "treatment" , variant_value = "treatment" )
367- self ._flags .track_exposure_event ("test_flag" , variant , {"distinct_id" : "user123" })
402+ self ._flags .track_exposure_event (TEST_FLAG_KEY , variant , {"distinct_id" : "user123" })
368403
369404 self ._mock_tracker .assert_called_once ()
370405
@@ -394,7 +429,7 @@ async def test_is_enabled_returns_true_for_true_variant_value(self):
394429 ]
395430 flag = create_test_flag (variants = variants , rollout_percentage = 100.0 )
396431 await self .setup_flags ([flag ])
397- result = self ._flags .is_enabled ("test_flag" , {"distinct_id" : "user123" })
432+ result = self ._flags .is_enabled (TEST_FLAG_KEY , {"distinct_id" : "user123" })
398433 assert result == True
399434
400435 @respx .mock
@@ -419,7 +454,7 @@ async def track_fetch_calls(self):
419454 async with polling_limit_check :
420455 await polling_limit_check .wait_for (lambda : polling_iterations >= len (flags_in_order ))
421456
422- result2 = self ._flags_with_polling .get_variant_value ("test_flag" , "fallback" , {"distinct_id" : "user123" })
457+ result2 = self ._flags_with_polling .get_variant_value (TEST_FLAG_KEY , "fallback" , {"distinct_id" : "user123" })
423458 assert result2 != "fallback"
424459
425460class TestLocalFeatureFlagsProviderSync :
@@ -465,5 +500,5 @@ def track_fetch_calls(self):
465500 self .setup_flags_with_polling (flags_in_order )
466501 polling_event .wait (timeout = 5.0 )
467502 assert (polling_iterations >= 3 )
468- result2 = self ._flags_with_polling .get_variant_value ("test_flag" , "fallback" , {"distinct_id" : "user123" })
503+ result2 = self ._flags_with_polling .get_variant_value (TEST_FLAG_KEY , "fallback" , {"distinct_id" : "user123" })
469504 assert result2 != "fallback"
0 commit comments