Inheritance: AnimalService, IDisposable
        public void Can_Resolve_Scoped_Type()
        {
            var services = new ServiceCollection();

            services.AddNamed <AnimalService>(names =>
            {
                names.AddScoped("A");
                names.AddScoped <DisposableTigerService>("B");
            });

            var sp       = services.BuildServiceProvider();
            var resolver = sp.GetRequiredService <NamedServiceResolver <AnimalService> >();

            var instanceA = resolver["A"];
            var instanceB = resolver["B"];

            Assert.NotSame(instanceA, instanceB);

            Assert.IsType <AnimalService>(instanceA);
            Assert.IsType <DisposableTigerService>(instanceB);


            // multiple resolves from same scope yields same instances.
            Assert.Same(instanceA, resolver["A"]);
            Assert.Same(instanceB, resolver["B"]);

            DisposableTigerService checkDisposed = null;

            using (var newScope = sp.CreateScope())
            {
                // initial resolve from  new scope yields new instance
                var scopedResolver = newScope.ServiceProvider.GetRequiredService <NamedServiceResolver <AnimalService> >();

                var newScopeInstanceA = scopedResolver["A"];
                var newScopeInstanceB = scopedResolver["B"];

                Assert.NotSame(newScopeInstanceA, instanceA);
                Assert.NotSame(newScopeInstanceB, instanceB);
                Assert.NotSame(newScopeInstanceA, newScopeInstanceB);

                // multiple resolves from same scope yields same instances.
                Assert.Same(newScopeInstanceA, scopedResolver["A"]);
                Assert.Same(newScopeInstanceB, scopedResolver["B"]);

                Assert.IsType <DisposableTigerService>(newScopeInstanceB);
                checkDisposed = (DisposableTigerService)newScopeInstanceB;
            }

            Assert.True(checkDisposed.WasDisposed);

            checkDisposed = (DisposableTigerService)instanceB;
            Assert.False(checkDisposed.WasDisposed);

            sp.Dispose();
            Assert.True(checkDisposed.WasDisposed);
        }
        public void Can_Dispose_Of_SingletonInstances()
        {
            var disposable = new DisposableTigerService() { SomeProperty = "Should be disposed." };
            var disposableShouldNotBeDisposed = new DisposableTigerService() { SomeProperty = "Should NOT be disposed." };

            using (var namedRegistrations = new NamedServiceRegistry<AnimalService>(GetDefaultServiceProvider()))
            {
                namedRegistrations.AddSingleton("A", disposableShouldNotBeDisposed);
                namedRegistrations.AddSingleton("B", disposable, registrationOwnsInstance: true); // This param defaults to false, must specifiy true if you want instance to be disposed by service provider dispose().
            }

            Assert.False(disposableShouldNotBeDisposed.WasDisposed);
            Assert.True(disposable.WasDisposed);
        }
        public void Owned_Singleton_Instances_Are_Disposed_When_ServiceProvider_Is_Disposed()
        {
            var disposable = new DisposableTigerService() { SomeProperty = "B" };

            var services = new ServiceCollection();
            services.AddNamed<AnimalService>(registry =>
            {
                registry.AddSingleton("A", new AnimalService() { SomeProperty = "A" });
                registry.AddSingleton("B", disposable, registrationOwnsInstance: true);
            });

            var sp = services.BuildServiceProvider();
            // before the container will dispose the registry (and thus the instances registered with the registry)
            // it must have first resolved an instance of it atleast once.
            var resolved = sp.GetRequiredService<NamedServiceRegistry<AnimalService>>();
            sp.Dispose();

            Assert.True(disposable.WasDisposed);
        }