Ejemplo n.º 1
0
        /// <summary>
        /// Resolves instances for the specified request. The instances are not actually resolved
        /// until a consumer iterates over the enumerator.
        /// </summary>
        /// <param name="request">The request to resolve.</param>
        /// <returns>An enumerator of instances that match the request.</returns>
        public virtual IEnumerable <object> Resolve(IRequest request)
        {
            Ensure.ArgumentNotNull(request, "request");

            if (request.Service == typeof(IKernel))
            {
                return new[] { this }
            }
            ;

            if (!CanResolve(request) && !HandleMissingBinding(request.Service))
            {
                if (request.IsOptional)
                {
                    return(Enumerable.Empty <object>());
                }
                else
                {
                    throw new ActivationException(ExceptionFormatter.CouldNotResolveBinding(request));
                }
            }

            return(GetBindings(request.Service)
                   .OrderBy(binding => binding.IsConditional ? 0 : 1)
                   .Where(binding => binding.Matches(request) && request.Matches(binding))
                   .Select(binding => CreateContext(request, binding))
                   .Select(context => context.Resolve()));
        }
Ejemplo n.º 2
0
        private IEnumerable <object> Resolve(IRequest request, bool handleMissingBindings)
        {
            var satisfiedBindings = this.GetBindings(request.Service)
                                    .Where(this.SatifiesRequest(request));
            var satisfiedBindingEnumerator = satisfiedBindings.GetEnumerator();

            if (!satisfiedBindingEnumerator.MoveNext())
            {
                if (handleMissingBindings && this.HandleMissingBinding(request))
                {
                    return(this.Resolve(request, false));
                }

                if (request.IsOptional)
                {
                    return(Enumerable.Empty <object>());
                }

                throw new ActivationException(ExceptionFormatter.CouldNotResolveBinding(request));
            }

            if (request.IsUnique)
            {
                var selectedBinding = satisfiedBindingEnumerator.Current;

                if (satisfiedBindingEnumerator.MoveNext() &&
                    bindingPrecedenceComparer.Compare(selectedBinding, satisfiedBindingEnumerator.Current) == 0)
                {
                    if (request.IsOptional && !request.ForceUnique)
                    {
                        return(Enumerable.Empty <object>());
                    }

                    var formattedBindings =
                        from binding in satisfiedBindings
                        let context = this.CreateContext(request, binding)
                                      select binding.Format(context);

                    throw new ActivationException(ExceptionFormatter.CouldNotUniquelyResolveBinding(request,
                                                                                                    formattedBindings.ToArray()));
                }

                return(new [] { this.CreateContext(request, selectedBinding).Resolve() });
            }
            else
            {
                if (satisfiedBindings.Any(binding => !binding.IsImplicit))
                {
                    satisfiedBindings = satisfiedBindings.Where(binding => !binding.IsImplicit);
                }

                return(satisfiedBindings
                       .Select(binding => this.CreateContext(request, binding).Resolve()));
            }
        }
Ejemplo n.º 3
0
        /// <summary>
        /// Resolves instances for the specified request. The instances are not actually resolved
        /// until a consumer iterates over the enumerator.
        /// </summary>
        /// <param name="request">The request to resolve.</param>
        /// <returns>An enumerator of instances that match the request.</returns>
        public virtual IEnumerable <object> Resolve(IRequest request)
        {
            Ensure.ArgumentNotNull(request, "request");

            var bindingPrecedenceComparer = this.GetBindingPrecedenceComparer();
            var resolveBindings           = Enumerable.Empty <IBinding>();

            if (this.CanResolve(request) || this.HandleMissingBinding(request))
            {
                resolveBindings = this.GetBindings(request.Service)
                                  .Where(this.SatifiesRequest(request));
            }

            if (!resolveBindings.Any())
            {
                if (request.IsOptional)
                {
                    return(Enumerable.Empty <object>());
                }

                throw new ActivationException(ExceptionFormatter.CouldNotResolveBinding(request));
            }

            if (request.IsUnique)
            {
                resolveBindings = resolveBindings.OrderByDescending(b => b, bindingPrecedenceComparer).ToList();
                var model = resolveBindings.First(); // the type (conditonal, implicit, etc) of binding we'll return
                resolveBindings =
                    resolveBindings.TakeWhile(binding => bindingPrecedenceComparer.Compare(binding, model) == 0);

                if (resolveBindings.Count() > 1)
                {
                    if (request.IsOptional)
                    {
                        return(Enumerable.Empty <object>());
                    }

                    var formattedBindings =
                        from binding in resolveBindings
                        let context = this.CreateContext(request, binding)
                                      select binding.Format(context);

                    throw new ActivationException(ExceptionFormatter.CouldNotUniquelyResolveBinding(request, formattedBindings.ToArray()));
                }
            }

            if (resolveBindings.Any(binding => !binding.IsImplicit))
            {
                resolveBindings = resolveBindings.Where(binding => !binding.IsImplicit);
            }

            return(resolveBindings
                   .Select(binding => this.CreateContext(request, binding).Resolve()));
        }
Ejemplo n.º 4
0
        private IEnumerable <object> ResolveWithMissingBindings(IRequest request, bool handleMissingBindings)
        {
            if (handleMissingBindings && this.HandleMissingBinding(request))
            {
                return(this.Resolve(request));
            }

            if (request.IsOptional)
            {
                return(Enumerable.Empty <object>());
            }

            throw new ActivationException(ExceptionFormatter.CouldNotResolveBinding(request));
        }
Ejemplo n.º 5
0
        /// <summary>
        /// Resolves instances for the specified request. The instances are not actually resolved
        /// until a consumer iterates over the enumerator.
        /// </summary>
        /// <param name="request">The request to resolve.</param>
        /// <returns>An enumerator of instances that match the request.</returns>
        public virtual IEnumerable <object> Resolve(IRequest request)
        {
            Ensure.ArgumentNotNull(request, "request");

            var bindingPrecedenceComparer = this.GetBindingPrecedenceComparer();
            var resolveBindings           = Enumerable.Empty <IBinding>();

            if (this.CanResolve(request) || this.HandleMissingBinding(request))
            {
                resolveBindings = this.GetBindings(request.Service)
                                  .Where(this.SatifiesRequest(request))
                                  .OrderByDescending(b => b, bindingPrecedenceComparer)
                                  .ToList();
            }

            if (!resolveBindings.Any())
            {
                if (request.IsOptional)
                {
                    return(Enumerable.Empty <object>());
                }

                throw new ActivationException(ExceptionFormatter.CouldNotResolveBinding(request));
            }

            var model = resolveBindings.First();

            resolveBindings = resolveBindings.TakeWhile(binding => bindingPrecedenceComparer.Compare(binding, model) == 0);

            if (request.IsUnique && resolveBindings.Count() > 1)
            {
                if (request.IsOptional)
                {
                    return(Enumerable.Empty <object>());
                }

                throw new ActivationException(ExceptionFormatter.CouldNotUniquelyResolveBinding(request));
            }

            return(resolveBindings.Select(binding => this.CreateContext(request, binding).Resolve()));
        }
Ejemplo n.º 6
0
        protected override IEnumerable <TService> Resolve <TService>(IRequest request, bool handleMissingBindings)
        {
            _ = request ?? throw new ArgumentNullException(nameof(request));

            var modBindings   = this.GetSatisfiedBindings(request).ToArray();
            var bindingGroups = modBindings.Where(binding => !binding.IsImplicit).ToList().Yield()
                                .Append(
                this.globalKernel.GetSatisfiedBindings(request).Where(binding => !this.IsProxyToThis(binding))
                .ToList()
                )
                                .Append(modBindings.Where(binding => binding.IsImplicit).ToList())
                                .Where(bindings => bindings.Any())
                                .ToList();

            var resolvedServices = new List <TService>();

            foreach (var satisfiedBindings in bindingGroups)
            {
                // Implicit bindings should only be added if there are no other matching bindings
                if (resolvedServices.Any() && satisfiedBindings.Any(binding => binding.IsImplicit))
                {
                    break;
                }

                if (request.IsUnique)
                {
                    if (satisfiedBindings.Count > 1 &&
                        this.BindingPrecedenceComparer.Compare(satisfiedBindings[0], satisfiedBindings[1]) == 0)
                    {
                        if (request.IsOptional && !request.ForceUnique)
                        {
                            return(Enumerable.Empty <TService>());
                        }

                        var formattedBindings = satisfiedBindings
                                                .Select(binding => binding.Format(this.CreateContext(request, binding)))
                                                .ToArray();

                        throw new ActivationException(
                                  ExceptionFormatter.CouldNotUniquelyResolveBinding(request, formattedBindings)
                                  );
                    }

                    return(((TService)this.CreateContext(request, satisfiedBindings[0]).Resolve()).Yield());
                }

                var services = satisfiedBindings
                               .Select(binding => this.CreateContext(request, binding).Resolve());
                resolvedServices.AddRange(
                    services
                    .Cast <TService>()
                    );
            }

            if (resolvedServices.Any())
            {
                return(resolvedServices);
            }

            if (handleMissingBindings && this.HandleMissingBinding(request))
            {
                return(this.Resolve <TService>(request, false));
            }

            if (request.IsOptional)
            {
                return(Enumerable.Empty <TService>());
            }

            throw new ActivationException(ExceptionFormatter.CouldNotResolveBinding(request));
        }
Ejemplo n.º 7
0
        private IEnumerable <object> Resolve(IRequest request, bool handleMissingBindings)
        {
            void UpdateRequest(Type service)
            {
                if (request.ParentRequest == null)
                {
                    request = this.CreateRequest(service, null, request.Parameters.Where(p => p.ShouldInherit), true, false);
                }
                else
                {
                    request            = request.ParentRequest.CreateChild(service, request.ParentContext, request.Target);
                    request.IsOptional = true;
                }
            }

            if (request.Service.IsArray)
            {
                var service = request.Service.GetElementType();

                UpdateRequest(service);

                return(new[] { this.Resolve(request, false).CastSlow(service).ToArraySlow(service) });
            }

            if (request.Service.IsGenericType)
            {
                var gtd = request.Service.GetGenericTypeDefinition();

                if (gtd == typeof(List <>) || gtd == typeof(IList <>) || gtd == typeof(ICollection <>))
                {
                    var service = request.Service.GenericTypeArguments[0];

                    UpdateRequest(service);

                    return(new[] { this.Resolve(request, false).CastSlow(service).ToListSlow(service) });
                }

                if (gtd == typeof(IEnumerable <>))
                {
                    var service = request.Service.GenericTypeArguments[0];

                    UpdateRequest(service);

                    return(new[] { this.Resolve(request, false).CastSlow(service) });
                }
            }

            var satisfiedBindings = this.GetBindings(request.Service)
                                    .Where(this.SatifiesRequest(request));
            var satisfiedBindingEnumerator = satisfiedBindings.GetEnumerator();

            if (!satisfiedBindingEnumerator.MoveNext())
            {
                if (handleMissingBindings && this.HandleMissingBinding(request))
                {
                    return(this.Resolve(request, false));
                }

                if (request.IsOptional)
                {
                    return(Enumerable.Empty <object>());
                }

                throw new ActivationException(ExceptionFormatter.CouldNotResolveBinding(request));
            }

            if (request.IsUnique)
            {
                var selectedBinding = satisfiedBindingEnumerator.Current;

                if (satisfiedBindingEnumerator.MoveNext() &&
                    this.bindingPrecedenceComparer.Compare(selectedBinding, satisfiedBindingEnumerator.Current) == 0)
                {
                    if (request.IsOptional && !request.ForceUnique)
                    {
                        return(Enumerable.Empty <object>());
                    }

                    var formattedBindings =
                        from binding in satisfiedBindings
                        let context = this.CreateContext(request, binding)
                                      select binding.Format(context);

                    throw new ActivationException(ExceptionFormatter.CouldNotUniquelyResolveBinding(
                                                      request,
                                                      formattedBindings.ToArray()));
                }

                return(new[] { this.CreateContext(request, selectedBinding).Resolve() });
            }
            else
            {
                if (satisfiedBindings.Any(binding => !binding.IsImplicit))
                {
                    satisfiedBindings = satisfiedBindings.Where(binding => !binding.IsImplicit);
                }

                return(satisfiedBindings
                       .Select(binding => this.CreateContext(request, binding).Resolve()));
            }
        }