private object GetHostProperty()

in ClearScript/HostItem.cs [1357:1513]


        private object GetHostProperty(string name, BindingFlags invokeFlags, object[] args, object[] bindArgs, CultureInfo culture, bool includeBoundMembers, out bool isCacheable)
        {
            isCacheable = false;

            if (name == SpecialMemberNames.Default)
            {
                var defaultProperty = Target.Type.GetScriptableDefaultProperty(invokeFlags, bindArgs, AccessContext, DefaultAccess);
                if (defaultProperty != null)
                {
                    return GetHostProperty(defaultProperty, invokeFlags, args, culture);
                }

                if (TargetDynamicMetaObject != null)
                {
                    if (TargetDynamicMetaObject.TryGetIndex(args, out var result))
                    {
                        return result;
                    }
                }

                return Nonexistent.Value;
            }

            if (name == SpecialMemberNames.NewEnum)
            {
                return CreateEnumerator();
            }

            if (name == SpecialMemberNames.NewAsyncEnum)
            {
                return CreateAsyncEnumerator();
            }

            if ((TargetDynamicMetaObject != null) && (args.Length < 1))
            {
                int index;
                object result;

                if (TargetDynamicMetaObject.HasMember(name, invokeFlags.HasFlag(BindingFlags.IgnoreCase)))
                {
                    if (TargetDynamicMetaObject.TryGetMember(name, out result))
                    {
                        return result;
                    }

                    if (int.TryParse(name, NumberStyles.Integer, CultureInfo.InvariantCulture, out index))
                    {
                        if (TargetDynamicMetaObject.TryGetIndex(new object[] { index }, out result))
                        {
                            return result;
                        }
                    }

                    if (TargetDynamicMetaObject.TryGetIndex(new object[] { name }, out result))
                    {
                        return result;
                    }

                    if (includeBoundMembers)
                    {
                        if (HostMethodMap == null)
                        {
                            HostMethodMap = new Dictionary<string, HostMethod>();
                        }

                        if (!HostMethodMap.TryGetValue(name, out var hostMethod))
                        {
                            hostMethod = new HostMethod(this, name);
                            HostMethodMap.Add(name, hostMethod);
                        }

                        return hostMethod;
                    }

                    return Nonexistent.Value;
                }

                if (int.TryParse(name, NumberStyles.Integer, CultureInfo.InvariantCulture, out index))
                {
                    if (TargetDynamicMetaObject.TryGetIndex(new object[] { index }, out result))
                    {
                        return result;
                    }
                }

                if (TargetDynamicMetaObject.TryGetIndex(new object[] { name }, out result))
                {
                    return result;
                }
            }

            var property = Target.Type.GetScriptableProperty(name, invokeFlags, bindArgs, AccessContext, DefaultAccess);
            if (property != null)
            {
                return GetHostProperty(property, invokeFlags, args, culture);
            }

            if (args.Length > 0)
            {
                throw new MissingMemberException(MiscHelpers.FormatInvariant("The object has no suitable property named '{0}'", name));
            }

            var eventInfo = Target.Type.GetScriptableEvent(name, invokeFlags, AccessContext, DefaultAccess);
            if (eventInfo != null)
            {
                var type = typeof(EventSource<>).MakeSpecificType(eventInfo.EventHandlerType);
                isCacheable = (TargetDynamicMetaObject == null);
                return type.CreateInstance(BindingFlags.NonPublic, Engine, Target.InvokeTarget, eventInfo);
            }

            var field = Target.Type.GetScriptableField(name, invokeFlags, AccessContext, DefaultAccess);
            if (field != null)
            {
                var result = field.GetValue(Target.InvokeTarget);
                isCacheable = (TargetDynamicMetaObject == null) && (field.IsLiteral || field.IsInitOnly);
                return Engine.PrepareResult(result, field.FieldType, field.GetScriptMemberFlags(), false);
            }

            if (includeBoundMembers)
            {
                if (Target.Type.GetScriptableProperties(name, invokeFlags, AccessContext, DefaultAccess).Any())
                {
                    if (HostIndexedPropertyMap == null)
                    {
                        HostIndexedPropertyMap = new Dictionary<string, HostIndexedProperty>();
                    }

                    if (!HostIndexedPropertyMap.TryGetValue(name, out var hostIndexedProperty))
                    {
                        hostIndexedProperty = new HostIndexedProperty(this, name);
                        HostIndexedPropertyMap.Add(name, hostIndexedProperty);
                    }

                    return hostIndexedProperty;
                }

                var method = ThisReflect.GetMethods(GetMethodBindFlags()).FirstOrDefault(testMethod => testMethod.Name == name);
                if (method != null)
                {
                    if (HostMethodMap == null)
                    {
                        HostMethodMap = new Dictionary<string, HostMethod>();
                    }

                    if (!HostMethodMap.TryGetValue(name, out var hostMethod))
                    {
                        hostMethod = new HostMethod(this, name);
                        HostMethodMap.Add(name, hostMethod);
                    }

                    isCacheable = (TargetDynamicMetaObject == null);
                    return hostMethod;
                }
            }

            return Nonexistent.Value;
        }