/// <summary>
 /// Adds the result of a flag evaluation.
 /// </summary>
 /// <param name="flagKey">the flag key</param>
 /// <param name="result">the evaluation result</param>
 /// <returns></returns>
 public FeatureFlagsStateBuilder AddFlag(string flagKey, EvaluationDetail <LdValue> result)
 {
     return(AddFlag(flagKey,
                    result?.Value.InnerValue,
                    result?.VariationIndex,
                    result?.Reason,
                    0,
                    false,
                    null));
 }
示例#2
0
 internal EvalResult(EvaluationDetail <JToken> result, IList <FeatureRequestEvent> events) : this()
 {
     Result             = result;
     PrerequisiteEvents = events;
 }
示例#3
0
        private EvaluationDetail <JToken> Evaluate(string featureKey, User user, JToken defaultValue, JTokenType?expectedType,
                                                   EventFactory eventFactory)
        {
            if (!Initialized())
            {
                if (_featureStore.Initialized())
                {
                    Log.Warn("Flag evaluation before client initialized; using last known values from feature store");
                }
                else
                {
                    Log.Warn("Flag evaluation before client initialized; feature store unavailable, returning default value");
                    return(new EvaluationDetail <JToken>(defaultValue, null,
                                                         new EvaluationReason.Error(EvaluationErrorKind.CLIENT_NOT_READY)));
                }
            }

            FeatureFlag featureFlag = null;

            try
            {
                featureFlag = _featureStore.Get(VersionedDataKind.Features, featureKey);
                if (featureFlag == null)
                {
                    Log.InfoFormat("Unknown feature flag {0}; returning default value",
                                   featureKey);

                    _eventProcessor.SendEvent(eventFactory.NewUnknownFeatureRequestEvent(featureKey, user, defaultValue,
                                                                                         EvaluationErrorKind.FLAG_NOT_FOUND));
                    return(new EvaluationDetail <JToken>(defaultValue, null,
                                                         new EvaluationReason.Error(EvaluationErrorKind.FLAG_NOT_FOUND)));
                }

                if (user == null || user.Key == null)
                {
                    Log.Warn("Feature flag evaluation called with null user or null user key. Returning default");
                    _eventProcessor.SendEvent(eventFactory.NewDefaultFeatureRequestEvent(featureFlag, user, defaultValue,
                                                                                         EvaluationErrorKind.USER_NOT_SPECIFIED));
                    return(new EvaluationDetail <JToken>(defaultValue, null,
                                                         new EvaluationReason.Error(EvaluationErrorKind.USER_NOT_SPECIFIED)));
                }

                FeatureFlag.EvalResult evalResult = featureFlag.Evaluate(user, _featureStore, eventFactory);
                if (!IsOffline())
                {
                    foreach (var prereqEvent in evalResult.PrerequisiteEvents)
                    {
                        _eventProcessor.SendEvent(prereqEvent);
                    }
                }
                var detail = evalResult.Result;
                if (detail.VariationIndex == null)
                {
                    detail = new EvaluationDetail <JToken>(defaultValue, null, detail.Reason);
                }
                if (detail.Value != null && !CheckResultType(expectedType, detail.Value))
                {
                    Log.ErrorFormat("Expected type: {0} but got {1} when evaluating FeatureFlag: {2}. Returning default",
                                    expectedType,
                                    detail.Value.GetType(),
                                    featureKey);

                    _eventProcessor.SendEvent(eventFactory.NewDefaultFeatureRequestEvent(featureFlag, user, defaultValue,
                                                                                         EvaluationErrorKind.WRONG_TYPE));
                    return(new EvaluationDetail <JToken>(defaultValue, null,
                                                         new EvaluationReason.Error(EvaluationErrorKind.WRONG_TYPE)));
                }
                _eventProcessor.SendEvent(eventFactory.NewFeatureRequestEvent(featureFlag, user, detail, defaultValue));
                return(detail);
            }
            catch (Exception e)
            {
                Log.ErrorFormat("Encountered exception in LaunchDarkly client: {0} when evaluating feature key: {1} for user key: {2}",
                                Util.ExceptionMessage(e),
                                featureKey,
                                user.Key);
                Log.Debug(e.ToString(), e);
                var detail = new EvaluationDetail <JToken>(defaultValue, null,
                                                           new EvaluationReason.Error(EvaluationErrorKind.EXCEPTION));
                if (featureFlag == null)
                {
                    _eventProcessor.SendEvent(eventFactory.NewUnknownFeatureRequestEvent(featureKey, user, defaultValue,
                                                                                         EvaluationErrorKind.EXCEPTION));
                }
                else
                {
                    _eventProcessor.SendEvent(eventFactory.NewFeatureRequestEvent(featureFlag, user,
                                                                                  detail, defaultValue));
                }
                return(detail);
            }
        }