예제 #1
0
        /// <summary>
        /// Determine variation the user should be put in.
        /// </summary>
        /// <param name="config">ProjectConfig Configuration for the project</param>
        /// <param name="experiment">Experiment Experiment in which user is to be bucketed</param>
        /// <param name="bucketingId">A customer-assigned value used to create the key for the murmur hash.</param>
        /// <param name="userId">User identifier</param>
        /// <returns>Variation which will be shown to the user</returns>
        public virtual Result <Variation> Bucket(ProjectConfig config, Experiment experiment, string bucketingId, string userId)
        {
            string    message;
            Variation variation;

            var reasons = new DecisionReasons();

            if (string.IsNullOrEmpty(experiment.Key))
            {
                return(Result <Variation> .NewResult(new Variation(), reasons));
            }

            // Determine if experiment is in a mutually exclusive group.
            if (experiment.IsInMutexGroup)
            {
                Group group = config.GetGroup(experiment.GroupId);
                if (string.IsNullOrEmpty(group.Id))
                {
                    return(Result <Variation> .NewResult(new Variation(), reasons));
                }

                string userExperimentId = FindBucket(bucketingId, userId, group.Id, group.TrafficAllocation);
                if (string.IsNullOrEmpty(userExperimentId))
                {
                    message = $"User [{userId}] is in no experiment.";
                    Logger.Log(LogLevel.INFO, reasons.AddInfo(message));
                    return(Result <Variation> .NewResult(new Variation(), reasons));
                }

                if (userExperimentId != experiment.Id)
                {
                    message = $"User [{userId}] is not in experiment [{experiment.Key}] of group [{experiment.GroupId}].";
                    Logger.Log(LogLevel.INFO, reasons.AddInfo(message));
                    return(Result <Variation> .NewResult(new Variation(), reasons));
                }

                message = $"User [{userId}] is in experiment [{experiment.Key}] of group [{experiment.GroupId}].";
                Logger.Log(LogLevel.INFO, reasons.AddInfo(message));
            }

            // Bucket user if not in whitelist and in group (if any).
            string variationId = FindBucket(bucketingId, userId, experiment.Id, experiment.TrafficAllocation);

            if (string.IsNullOrEmpty(variationId))
            {
                Logger.Log(LogLevel.INFO, reasons.AddInfo($"User [{userId}] is in no variation."));
                return(Result <Variation> .NewResult(new Variation(), reasons));
            }

            // success!
            variation = config.GetVariationFromIdByExperimentId(experiment.Id, variationId);
            message   = $"User [{userId}] is in variation [{variation.Key}] of experiment [{experiment.Key}].";
            Logger.Log(LogLevel.INFO, reasons.AddInfo(message));
            return(Result <Variation> .NewResult(variation, reasons));
        }