Пример #1
0
        public override DynamicMetaObject BindGetMember(GetMemberBinder binder)
        {
            var metaObj = base.BindGetMember(binder);

            var property = _objType.GetProperty(binder.Name,
                                                BindingFlags.DeclaredOnly | BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic);

            if (property != null && property.IsDefined(typeof(IAspect), false))
            {
                var aspects = RetrieveAspects(property);
                metaObj = new GetterGenerator(Value, metaObj.Restrictions, aspects, property).Generate();
            }
            return(metaObj);
        }
Пример #2
0
        private static bool LinkEncoder <T>(IEncoderDescriptor <T> descriptor, BindingFlags bindings,
                                            IDictionary <Type, object> parents)
        {
            var entityType = typeof(T);

            parents[entityType] = descriptor;

            if (Linker.TryLinkEncoderAsValue(descriptor))
            {
                return(true);
            }

            // Bind descriptor as an array of target type is also array
            if (entityType.IsArray)
            {
                var element = entityType.GetElementType();
                var getter  = MethodResolver
                              .Create <Func <Func <object, object> > >(() => GetterGenerator.CreateIdentity <object>())
                              .SetGenericArguments(typeof(IEnumerable <>).MakeGenericType(element))
                              .Invoke(null);

                return(Linker.LinkEncoderAsArray(descriptor, bindings, element, getter, parents));
            }

            // Try to bind descriptor as an array if target type IEnumerable<>
            foreach (var interfaceType in entityType.GetInterfaces())
            {
                // Make sure that interface is IEnumerable<T> and store typeof(T)
                if (!TypeResolver.Create(interfaceType).HasSameDefinitionThan <IEnumerable <object> >(out var arguments))
                {
                    continue;
                }

                var elementType = arguments[0];
                var getter      = MethodResolver
                                  .Create <Func <Func <object, object> > >(() => GetterGenerator.CreateIdentity <object>())
                                  .SetGenericArguments(typeof(IEnumerable <>).MakeGenericType(elementType))
                                  .Invoke(null);

                return(Linker.LinkEncoderAsArray(descriptor, bindings, elementType, getter, parents));
            }

            // Bind readable and writable instance properties
            foreach (var property in entityType.GetProperties(bindings))
            {
                if (property.GetGetMethod() == null || property.GetSetMethod() == null ||
                    property.Attributes.HasFlag(PropertyAttributes.SpecialName))
                {
                    continue;
                }

                var getter = MethodResolver
                             .Create <Func <PropertyInfo, Func <object, object> > >(p =>
                                                                                    GetterGenerator.CreateFromProperty <object, object>(p))
                             .SetGenericArguments(entityType, property.PropertyType)
                             .Invoke(null, property);

                if (!Linker.LinkEncoderAsObject(descriptor, bindings, property.PropertyType, property.Name, getter,
                                                parents))
                {
                    return(false);
                }
            }

            // Bind public instance fields
            foreach (var field in entityType.GetFields(bindings))
            {
                if (field.Attributes.HasFlag(FieldAttributes.SpecialName))
                {
                    continue;
                }

                var getter = MethodResolver
                             .Create <Func <FieldInfo, Func <object, object> > >(f =>
                                                                                 GetterGenerator.CreateFromField <object, object>(f))
                             .SetGenericArguments(entityType, field.FieldType)
                             .Invoke(null, field);

                if (!Linker.LinkEncoderAsObject(descriptor, bindings, field.FieldType, field.Name, getter, parents))
                {
                    return(false);
                }
            }

            return(true);
        }