public static object GetValue <T>(Expression <Func <RavenConfiguration, T> > getKey, RavenConfiguration serverConfiguration, Dictionary <string, string> settings)
        {
            TimeUnitAttribute timeUnit = null;

            var property = (PropertyInfo)getKey.ToProperty();

            if (property.PropertyType == typeof(TimeSetting) ||
                property.PropertyType == typeof(TimeSetting?))
            {
                timeUnit = property.GetCustomAttribute <TimeUnitAttribute>();
                Debug.Assert(timeUnit != null);
            }

            object value = null;

            foreach (var entry in property
                     .GetCustomAttributes <ConfigurationEntryAttribute>()
                     .OrderBy(x => x.Order))
            {
                if (settings.TryGetValue(entry.Key, out var valueAsString) == false)
                {
                    value = serverConfiguration.GetSetting(entry.Key);
                }

                if (valueAsString != null)
                {
                    value = valueAsString;
                    break;
                }
            }

            if (value == null)
            {
                value = GetDefaultValue(getKey);
            }

            if (value == null)
            {
                return(null);
            }

            if (timeUnit != null)
            {
                return(new TimeSetting(Convert.ToInt64(value), timeUnit.Unit));
            }

            throw new NotSupportedException("Cannot get value of a property of type: " + property.PropertyType.Name);
        }
        public ConfigurationEntryDatabaseValue(RavenConfiguration configuration, DatabaseRecord dbRecord, ConfigurationEntryMetadata metadata, RavenServer.AuthenticationStatus authenticationStatus)
            : base(configuration.ServerWideSettings, metadata, authenticationStatus)
        {
            if (Metadata.Scope == ConfigurationEntryScope.ServerWideOnly)
            {
                return;
            }

            DatabaseValues = new Dictionary <string, ConfigurationEntrySingleValue>();
            foreach (var key in Metadata.Keys)
            {
                bool canShowValue = Metadata.IsSecured == false;

                var hasValue = configuration.DoesKeyExistInSettings(key);
                var value    = configuration.GetSetting(key);

                if (dbRecord.Settings.TryGetValue(key, out var valueInDbRecord) == false)
                {
                    if (hasValue &&
                        string.Equals(key, RavenConfiguration.GetKey(x => x.Core.DataDirectory), StringComparison.OrdinalIgnoreCase) == false &&
                        string.Equals(key, RavenConfiguration.GetKey(x => x.Core.RunInMemory), StringComparison.OrdinalIgnoreCase) == false) // DataDirectory and RunInMemory are always set as in-memory values
                    {
                        // key does not exist in db record but current configuration has a value - deletion of an override is pending

                        DatabaseValues[key] = new ConfigurationEntrySingleValue
                        {
                            Value        = canShowValue ? value : null,
                            HasAccess    = true,
                            PendingValue = new ConfigurationEntrySinglePendingValue()
                            {
                                ValueDeleted = true,
                            }
                        };
                    }

                    continue;
                }

                string pendingValue    = null;
                var    hasPendingValue = false;

                if (hasValue)
                {
                    if (string.Equals(value, valueInDbRecord) == false)
                    {
                        pendingValue    = valueInDbRecord;
                        hasPendingValue = true;
                    }
                }
                else
                {
                    pendingValue    = valueInDbRecord;
                    hasPendingValue = true;
                }

                DatabaseValues[key] = new ConfigurationEntrySingleValue
                {
                    Value        = canShowValue ? value : null,
                    HasValue     = hasValue,
                    HasAccess    = true,
                    PendingValue = hasPendingValue == false ? null : new ConfigurationEntrySinglePendingValue()
                    {
                        HasValue = true,
                        Value    = canShowValue ? pendingValue : null
                    }
                };
            }
        }