1
- # Copyright 2016-2017, 2019-2020 Optimizely
1
+ # Copyright 2016-2017, 2019-2021 Optimizely
2
2
# Licensed under the Apache License, Version 2.0 (the "License");
3
3
# you may not use this file except in compliance with the License.
4
4
# You may obtain a copy of the License at
@@ -71,13 +71,13 @@ def find_bucket(self, project_config, bucketing_id, parent_id, traffic_allocatio
71
71
traffic_allocations: Traffic allocations representing traffic allotted to experiments or variations.
72
72
73
73
Returns:
74
- Entity ID which may represent experiment or variation.
74
+ Entity ID which may represent experiment or variation and
75
75
"""
76
-
77
76
bucketing_key = BUCKETING_ID_TEMPLATE .format (bucketing_id = bucketing_id , parent_id = parent_id )
78
77
bucketing_number = self ._generate_bucket_value (bucketing_key )
78
+ message = 'Assigned bucket %s to user with bucketing ID "%s".' % (bucketing_number , bucketing_id )
79
79
project_config .logger .debug (
80
- 'Assigned bucket %s to user with bucketing ID "%s".' % ( bucketing_number , bucketing_id )
80
+ message
81
81
)
82
82
83
83
for traffic_allocation in traffic_allocations :
@@ -97,41 +97,57 @@ def bucket(self, project_config, experiment, user_id, bucketing_id):
97
97
bucketing_id: ID to be used for bucketing the user.
98
98
99
99
Returns:
100
- Variation in which user with ID user_id will be put in. None if no variation.
100
+ Variation in which user with ID user_id will be put in. None if no variation
101
+ and array of log messages representing decision making.
102
+ */.
101
103
"""
102
-
104
+ decide_reasons = []
103
105
if not experiment :
104
- return None
106
+ return None , decide_reasons
105
107
106
108
# Determine if experiment is in a mutually exclusive group.
107
109
# This will not affect evaluation of rollout rules.
108
110
if experiment .groupPolicy in GROUP_POLICIES :
109
111
group = project_config .get_group (experiment .groupId )
110
112
111
113
if not group :
112
- return None
114
+ return None , decide_reasons
113
115
114
116
user_experiment_id = self .find_bucket (
115
117
project_config , bucketing_id , experiment .groupId , group .trafficAllocation ,
116
118
)
119
+
117
120
if not user_experiment_id :
118
- project_config .logger .info ('User "%s" is in no experiment.' % user_id )
119
- return None
121
+ message = 'User "%s" is in no experiment.' % user_id
122
+ project_config .logger .info (message )
123
+ decide_reasons .append (message )
124
+ return None , decide_reasons
120
125
121
126
if user_experiment_id != experiment .id :
127
+ message = 'User "%s" is not in experiment "%s" of group %s.' \
128
+ % (user_id , experiment .key , experiment .groupId )
122
129
project_config .logger .info (
123
- 'User "%s" is not in experiment "%s" of group %s.' % ( user_id , experiment . key , experiment . groupId )
130
+ message
124
131
)
125
- return None
132
+ decide_reasons .append (message )
133
+ return None , decide_reasons
126
134
135
+ message = 'User "%s" is in experiment %s of group %s.' % (user_id , experiment .key , experiment .groupId )
127
136
project_config .logger .info (
128
- 'User "%s" is in experiment %s of group %s.' % ( user_id , experiment . key , experiment . groupId )
137
+ message
129
138
)
139
+ decide_reasons .append (message )
130
140
131
141
# Bucket user if not in white-list and in group (if any)
132
- variation_id = self .find_bucket (project_config , bucketing_id , experiment .id , experiment .trafficAllocation )
142
+ variation_id = self .find_bucket (project_config , bucketing_id ,
143
+ experiment .id , experiment .trafficAllocation )
133
144
if variation_id :
134
145
variation = project_config .get_variation_from_id (experiment .key , variation_id )
135
- return variation
146
+ return variation , decide_reasons
136
147
137
- return None
148
+ else :
149
+ message = 'Bucketed into an empty traffic range. Returning nil.'
150
+ project_config .logger .info (message )
151
+ decide_reasons .append (message )
152
+
153
+ return None , decide_reasons
0 commit comments