Пример #1
0
        /// <summary>
        /// Create a new instance of <see cref="MessageParameterResolver"/>.
        /// </summary>
        /// <param name="maxLengthOfString"></param>
        /// <param name="maxLevelOfNestLevelLimited"></param>
        /// <param name="maxLoopCountForCollection"></param>
        /// <param name="additionalScalarTypes"></param>
        /// <param name="additionalDestructureResolveRules"></param>
        /// <param name="raiseExceptions"></param>
        /// <exception cref="ArgumentOutOfRangeException"></exception>
        /// <exception cref="ArgumentNullException"></exception>
        public MessageParameterResolver(
            int maxLengthOfString,
            int maxLevelOfNestLevelLimited,
            int maxLoopCountForCollection,
            IEnumerable <Type> additionalScalarTypes,
            IEnumerable <IDestructureResolveRule> additionalDestructureResolveRules,
            bool raiseExceptions)
        {
            if (maxLengthOfString < 2)
            {
                throw new ArgumentOutOfRangeException(nameof(maxLengthOfString));
            }
            if (maxLevelOfNestLevelLimited < 0)
            {
                throw new ArgumentOutOfRangeException(nameof(maxLevelOfNestLevelLimited));
            }
            if (maxLoopCountForCollection < 1)
            {
                throw new ArgumentOutOfRangeException(nameof(maxLoopCountForCollection));
            }
            if (additionalScalarTypes == null)
            {
                throw new ArgumentNullException(nameof(additionalScalarTypes));
            }
            if (additionalDestructureResolveRules == null)
            {
                throw new ArgumentNullException(nameof(additionalDestructureResolveRules));
            }

            _maxLengthOfString          = maxLengthOfString;
            _maxLevelOfNestLevelLimited = maxLevelOfNestLevelLimited;
            _maxLoopCountForCollection  = maxLoopCountForCollection;
            _raiseExceptions            = raiseExceptions;
            _scalarResolveRules         = new IScalarResolveRule[] {
                new SimpleResolveRule(additionalScalarTypes.GetAllScalarTypes()),
                new EnumResolveRule(), new ByteArrayResolveRule()
            };
            _destructureResolveRules = additionalDestructureResolveRules
                                       .Concat(new IDestructureResolveRule[] { new DelegateResolveRule(), new ReflectionTypesResolveRule() })
                                       .ToArray();
            _nestParameterResolver = new NestParameterResolver(_maxLevelOfNestLevelLimited, this);
        }
Пример #2
0
        public static bool TryResolveCompilerGeneratedType(object value, PropertyResolvingMode mode, NestParameterResolver nest, Type typeOfValue,
                                                           bool raiseException, int positionalValue, out MessagePropertyValue result)
        {
            if (mode == PropertyResolvingMode.Destructure)
            {
                result = new StructureValue(StructureElements(), Tag());
                return(true);

                string Tag()
                {
                    var __tag = typeOfValue.Name;

                    if (string.IsNullOrWhiteSpace(__tag) || typeOfValue.IsCompilerGeneratedType())
                    {
                        __tag = null;
                    }
                    return(__tag);
                }

                IEnumerable <MessageProperty> StructureElements()
                {
                    foreach (var property in value.GetType().GetPropertiesRecursive())
                    {
                        dynamic propertyValue;
                        try {
                            propertyValue = property.GetValue(value);
                        }
                        catch (TargetParameterCountException) {
                            InternalLogger.WriteLine("The property accessor '{0}' is a non-default indexer", property);
                            continue;
                        }
                        catch (TargetInvocationException ex) {
                            InternalLogger.WriteLine("The property accessor '{0}' threw exception: {1}", property, ex);
                            if (raiseException)
                            {
                                throw;
                            }
                            propertyValue = $"Threw an exception at: {ex.InnerException?.GetType().Name}";
                        }

                        yield return(new MessageProperty(property.Name, positionalValue, nest.CreatePropertyValue(propertyValue, PropertyResolvingMode.Destructure)));
                    }
                }
            }

            result = null;
            return(false);
        }
Пример #3
0
        public static bool TryResolveToValueTuple(object value, PropertyResolvingMode mode, NestParameterResolver nest, Type typeOfValue,
                                                  out MessagePropertyValue result)
        {
            result = CheckingValueTypeDefinition(typeOfValue, value) ? new SequenceValue(SequenceElements()) : null;
            return(result != null);

            IEnumerable <MessagePropertyValue> SequenceElements()
            {
                var __fields = typeOfValue.GetTypeInfo().DeclaredFields.Where(f => f.IsPublic && !f.IsStatic);

                foreach (var __field in __fields)
                {
                    yield return(nest.CreatePropertyValue(__field.GetValue(value), mode));
                }
            }
        }
Пример #4
0
        public static bool TryResolveToEnumerable(object value, PropertyResolvingMode mode, NestParameterResolver nest, Type typeOfValue,
                                                  int maxLoopCountForCollection, out MessagePropertyValue result)
        {
            if (value is IEnumerable __enumerable)
            {
                if (TryGetDictionary(value, typeOfValue, out var dictionary))
                {
                    result = new DictionaryValue(DictionaryElements());
                    return(true);

                    IEnumerable <KeyValuePair <ScalarValue, MessagePropertyValue> > DictionaryElements()
                    {
                        var __index = 0;

                        foreach (DictionaryEntry __item in dictionary)
                        {
                            if (++__index > maxLoopCountForCollection)
                            {
                                yield break;
                            }
                            if (nest.CreatePropertyValue(__item.Key, mode) is ScalarValue __key)
                            {
                                var __value = nest.CreatePropertyValue(__item.Value, mode);
                                yield return(new KeyValuePair <ScalarValue, MessagePropertyValue>(__key, __value));
                            }
                        }
                    }
                }

                result = new SequenceValue(SequenceElements());
                return(true);

                IEnumerable <MessagePropertyValue> SequenceElements()
                {
                    var __index = 0;

                    foreach (var __item in __enumerable)
                    {
                        if (++__index > maxLoopCountForCollection)
                        {
                            yield break;
                        }
                        yield return(nest.CreatePropertyValue(__item, mode));
                    }
                }
            }

            result = null;
            return(false);
        }