/// <summary>
        /// Registers all supplied <paramref name="implementationTypes"/> based on the closed-generic version
        /// of the given <paramref name="openGenericServiceType"/> with the given <paramref name="lifestyle"/>.
        /// </summary>
        /// <param name="openGenericServiceType">The definition of the open generic type.</param>
        /// <param name="implementationTypes">A list types to be registered.</param>
        /// <param name="lifestyle">The lifestyle to register instances with.</param>
        /// <exception cref="ArgumentNullException">Thrown when one of the arguments contain a null
        /// reference (Nothing in VB).</exception>
        /// <exception cref="ArgumentException">Thrown when <paramref name="openGenericServiceType"/> is not
        /// an open generic type or when one of the supplied types from the
        /// <paramref name="implementationTypes"/> collection does not derive from
        /// <paramref name="openGenericServiceType"/>.</exception>
        /// <exception cref="InvalidOperationException">Thrown when the given set of
        /// <paramref name="implementationTypes"/> contain multiple types that implement the same
        /// closed generic version of the given <paramref name="openGenericServiceType"/>.</exception>
        public void Register(Type openGenericServiceType, IEnumerable <Type> implementationTypes, Lifestyle lifestyle)
        {
            Requires.IsNotNull(openGenericServiceType, nameof(openGenericServiceType));
            Requires.IsNotNull(lifestyle, nameof(lifestyle));
            Requires.IsNotNull(implementationTypes, nameof(implementationTypes));
            Requires.IsGenericType(openGenericServiceType, nameof(openGenericServiceType),
                                   guidance: StringResources.SuppliedTypeIsNotGenericExplainingAlternativesWithTypes);
            Requires.IsNotPartiallyClosed(openGenericServiceType, nameof(openGenericServiceType));
            Requires.IsOpenGenericType(openGenericServiceType, nameof(openGenericServiceType),
                                       guidance: StringResources.SuppliedTypeIsNotOpenGenericExplainingAlternativesWithTypes);

            implementationTypes = implementationTypes.Distinct().ToArray();

            Requires.DoesNotContainNullValues(implementationTypes, nameof(implementationTypes));
            Requires.CollectionDoesNotContainOpenGenericTypes(implementationTypes, nameof(implementationTypes));
            Requires.ServiceIsAssignableFromImplementations(openGenericServiceType, implementationTypes,
                                                            nameof(implementationTypes), typeCanBeServiceType: false);

            var mappings =
                from mapping in BatchMapping.Build(openGenericServiceType, implementationTypes)
                let registration = lifestyle.CreateRegistration(mapping.ImplementationType, this)
                                   from serviceType in mapping.ClosedServiceTypes
                                   select new { serviceType, registration };

            foreach (var mapping in mappings)
            {
                this.AddRegistration(mapping.serviceType, mapping.registration);
            }
        }
        private ContainerControlledCollection <TService> CreateInternal <TService>(
            IEnumerable <Type> serviceTypes)
            where TService : class
        {
            Requires.IsNotAnAmbiguousType(typeof(TService), nameof(TService));
            Requires.IsNotNull(serviceTypes, nameof(serviceTypes));

            // Make a copy for correctness and performance.
            serviceTypes = serviceTypes.ToArray();

            Requires.DoesNotContainNullValues(serviceTypes, nameof(serviceTypes));
            Requires.ServiceIsAssignableFromImplementations(typeof(TService), serviceTypes, nameof(serviceTypes),
                                                            typeCanBeServiceType: true);
            Requires.DoesNotContainOpenGenericTypesWhenServiceTypeIsNotGeneric(typeof(TService), serviceTypes,
                                                                               nameof(serviceTypes));
            Requires.OpenGenericTypesDoNotContainUnresolvableTypeArguments(typeof(TService), serviceTypes,
                                                                           nameof(serviceTypes));

            var collection = new ContainerControlledCollection <TService>(this.container);

            collection.AppendAll(serviceTypes);

            this.RegisterForVerification(collection);

            return(collection);
        }
        /// <summary>
        /// Registers a collection of <paramref name="registrations"/>, whose instances will be resolved lazily
        /// each time the resolved collection of <paramref name="serviceType"/> is enumerated.
        /// The underlying collection is a stream that will return individual instances based on their
        /// specific registered lifestyle, for each call to <see cref="IEnumerator{T}.Current"/>.
        /// The order in which the types appear in the collection is the exact same order that the items were
        /// registered, i.e the resolved collection is deterministic.
        /// </summary>
        /// <param name="serviceType">The base type or interface for elements in the collection. This can be
        /// an a non-generic type, closed generic type or generic type definition.</param>
        /// <param name="registrations">The collection of <see cref="Registration"/> objects whose instances
        /// will be requested from the container.</param>
        /// <exception cref="ArgumentNullException">Thrown when one of the supplied arguments is a null
        /// reference (Nothing in VB).
        /// </exception>
        /// <exception cref="ArgumentException">Thrown when <paramref name="registrations"/> contains a null
        /// (Nothing in VB) element or when <paramref name="serviceType"/> is not assignable from any of the
        /// service types supplied by the given <paramref name="registrations"/> instances.
        /// </exception>
        public void RegisterCollection(Type serviceType, IEnumerable <Registration> registrations)
        {
            Requires.IsNotNull(serviceType, "serviceType");
            Requires.IsNotNull(registrations, "registrations");

            // Make a copy for performance and correctness.
            registrations = registrations.ToArray();

            Requires.DoesNotContainNullValues(registrations, "registrations");
            Requires.AreRegistrationsForThisContainer(this, registrations, "registrations");
            Requires.ServiceIsAssignableFromImplementations(serviceType, registrations, "registrations", typeCanBeServiceType: true);
            Requires.OpenGenericTypesDoNotContainUnresolvableTypeArguments(serviceType, registrations, "registrations");

            this.RegisterCollectionInternal(serviceType, registrations);
        }
        /// <summary>
        /// Registers a collection of <paramref name="serviceTypes"/>, whose instances will be resolved lazily
        /// each time the resolved collection of <paramref name="serviceType"/> is enumerated.
        /// The underlying collection is a stream that will return individual instances based on their
        /// specific registered lifestyle, for each call to <see cref="IEnumerator{T}.Current"/>.
        /// The order in which the types appear in the collection is the exact same order that the items were
        /// registered, i.e the resolved collection is deterministic.
        /// </summary>
        /// <param name="serviceType">The base type or interface for elements in the collection.</param>
        /// <param name="serviceTypes">The collection of <see cref="Type"/> objects whose instances
        /// will be requested from the container.</param>
        /// <exception cref="ArgumentNullException">Thrown when one of the supplied arguments is a null
        /// reference (Nothing in VB).
        /// </exception>
        /// <exception cref="ArgumentException">Thrown when <paramref name="serviceTypes"/> contains a null
        /// (Nothing in VB) element, a generic type definition, or the <paramref name="serviceType"/> is
        /// not assignable from one of the given <paramref name="serviceTypes"/> elements.
        /// </exception>
        public void RegisterCollection(Type serviceType, IEnumerable <Type> serviceTypes)
        {
            Requires.IsNotNull(serviceType, "serviceType");
            Requires.IsNotNull(serviceTypes, "serviceTypes");

            // Make a copy for correctness and performance.
            serviceTypes = serviceTypes.ToArray();

            Requires.DoesNotContainNullValues(serviceTypes, "serviceTypes");
            Requires.ServiceIsAssignableFromImplementations(serviceType, serviceTypes, "serviceTypes",
                                                            typeCanBeServiceType: true);
            Requires.DoesNotContainOpenGenericTypesWhenServiceTypeIsNotGeneric(serviceType, serviceTypes,
                                                                               "serviceTypes");
            Requires.OpenGenericTypesDoNotContainUnresolvableTypeArguments(serviceType, serviceTypes, "serviceTypes");

            this.RegisterCollectionInternal(serviceType, serviceTypes);
        }
示例#5
0
        public void RegisterCollection <TService>(params TService[] singletons) where TService : class
        {
            Requires.IsNotNull(singletons, nameof(singletons));
            Requires.DoesNotContainNullValues(singletons, nameof(singletons));

            if (typeof(TService) == typeof(Type) && singletons.Any())
            {
                throw new ArgumentException(
                          StringResources.RegisterCollectionCalledWithTypeAsTService(singletons.Cast <Type>()),
                          nameof(TService));
            }

            Requires.IsNotAnAmbiguousType(typeof(TService), nameof(TService));

            var singletonRegistrations =
                from singleton in singletons
                select SingletonLifestyle.CreateSingleInstanceRegistration(typeof(TService), singleton, this,
                                                                           singleton.GetType());

            this.RegisterCollection(typeof(TService), singletonRegistrations);
        }
        private ContainerControlledCollection <TService> CreateInternal <TService>(
            IEnumerable <Registration> registrations)
            where TService : class
        {
            Requires.IsNotAnAmbiguousType(typeof(TService), nameof(TService));
            Requires.IsNotNull(registrations, nameof(registrations));

            Requires.DoesNotContainNullValues(registrations, nameof(registrations));
            Requires.AreRegistrationsForThisContainer(this.container, registrations, nameof(registrations));
            Requires.ServiceIsAssignableFromImplementations(typeof(TService), registrations, nameof(registrations),
                                                            typeCanBeServiceType: true);
            Requires.OpenGenericTypesDoNotContainUnresolvableTypeArguments(typeof(TService), registrations,
                                                                           nameof(registrations));

            var collection = new ContainerControlledCollection <TService>(this.container);

            collection.AppendAll(registrations);

            this.RegisterForVerification(collection);

            return(collection);
        }