Skip to content

Flowing Scoped Lifestyle and Scoped Collection resolve #948

@Glunder0

Description

@Glunder0

When DefaultScopedLifestyle is set to ScopedLifestyle.Flowing collection elements that are registered as Scoped can be only resolved from the first scope. Trying to resolve them in any consequent scope throws an exception.

var container = new Container();
container.Options.DefaultScopedLifestyle = ScopedLifestyle.Flowing;
container.Collection.Append<IInterface, Instance>(Lifestyle.Scoped);

using (var scope = new Scope(container))
{
    scope.GetInstance<IInterface[]>(); // Ok
}

using (var scope = new Scope(container))
{
    scope.GetInstance<IInterface[]>(); // Exception
}
Unhandled exception. SimpleInjector.ActivationException: Cannot access a disposed object.
Object name: 'SimpleInjector.Scope'.
 ---> System.ObjectDisposedException: Cannot access a disposed object.
Object name: 'SimpleInjector.Scope'.
   at SimpleInjector.Scope.ThrowObjectDisposedException()
   at SimpleInjector.Scope.GetInstanceInternal(ScopedRegistration registration)
   at SimpleInjector.Scope.GetInstance[TImplementation](ScopedRegistration registration, Scope scope)
   at SimpleInjector.Advanced.Internal.LazyScopedRegistration`1.GetInstance(Scope scope)
   at lambda_method7(Closure )
   at SimpleInjector.InstanceProducer.GetInstance()
   --- End of inner exception stack trace ---
   at SimpleInjector.InstanceProducer.GetInstance()
   at SimpleInjector.Internals.ContainerControlledCollection`1.CopyTo(TService[] array, Int32 arrayIndex)
   at SimpleInjector.Internals.FlowingContainerControlledCollection`1.CopyTo(TService[] array, Int32 arrayIndex)
   at System.Collections.Generic.EnumerableHelpers.ToArray[T](IEnumerable`1 source)
   at System.Linq.Enumerable.ToArray[TSource](IEnumerable`1 source)
   at SimpleInjector.InstanceProducer.GetInstance()
   at SimpleInjector.Container.GetInstance(Type serviceType)
   at SimpleInjector.Scope.GetInstance(Type serviceType)
   at SimpleInjector.Scope.GetInstance[TService]()

And there is a difference in resolving scoped collections and resolving scoped single instances with DefaultScopedLifestyle set to ScopedLifestyle.Flowing.

var container = new Container();
container.Options.DefaultScopedLifestyle = ScopedLifestyle.Flowing;
container.Register<IInterface, Instance>(Lifestyle.Scoped);
container.Collection.Append<IInterface, Instance>(Lifestyle.Scoped);

var scopeOne = new Scope(container);
var singleInstanceOne = scopeOne.GetInstance<IInterface>();
var collectionInstanceOne = scopeOne.GetInstance<IInterface[]>()[0];

var scopeTwo = new Scope(container);
var singleInstanceTwo = scopeTwo.GetInstance<IInterface>();
var collectionInstanceTwo = scopeTwo.GetInstance<IInterface[]>()[0];

Console.WriteLine(singleInstanceOne.Equals(singleInstanceTwo)); // False
Console.WriteLine(collectionInstanceOne.Equals(collectionInstanceTwo)); // True

Metadata

Metadata

Assignees

No one assigned

    Labels

    Projects

    No projects

    Milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions