Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

PerScopeLifetime registered objects not calling Dispose reliably #529

Open
replaysMike opened this issue May 4, 2020 · 1 comment
Open

Comments

@replaysMike
Copy link

replaysMike commented May 4, 2020

I've run into an issue where it seems objects registered with PerScopeLifetime aren't having their Dispose() method called unless something holds a reference to it. It would seem if nothing calls GetInstance<> on that type then it won't be added to the objects to dispose list.

This may be due to trying to register a single instance of the object, but can't use RegisterInstance as it doesn't call Dispose when the container is disposed.

For example:

using (var container = new ServiceContainer(new ContainerOptions { EnablePropertyInjection = false }))
{
    using (var scope = container.BeginScope())
    {
        RegisterIOC();
    }
}
// assume myClass is available somewhere, I confirmed this with logging code
Assert.AreTrue(myClass.IsDisposed); // false

private void RegisterIOC() 
{
       // register singleton instance using scopelifetime so it is disposed
       var myClass = new MyClass();
       container.Register<MyClass>(f => myClass, nameof(MyClass), new PerScopeLifetime());
 }

public class MyClass : IDisposable 
{
    public bool IsDisposed = false;
    public void Dispose() { IsDisposed = true; }
}

where if I hold a reference to it the Dispose method gets called:

MyClass myClass = null;
using (var container = new ServiceContainer(new ContainerOptions { EnablePropertyInjection = false }))
{
    using (var scope = container.BeginScope())
    {
        RegisterIOC();
        myClass = container.GetInstance<MyClass>();
    }
}
Assert.AreTrue(myClass.IsDisposed); // true
@julealgon
Copy link

I wonder if this behavior is intentional. I could see that being the case if the semantic was "the container only disposes of things created by itself" in the sense that it will only track an object after someone has requested it from the container, but will ignore the instance if it was only provided but not used by the container itself leaving the responsibility to the caller to dispose of it.

Some other containers follow this at least partially: where providing an instance manually (like in the example) works different than registering the instance with a factory for example, even if both are Singleton/PerContainer registrations. In the former, the container doesn't try to "manage" the instance since it was not the one who created it, while in the latter it does.

Would be nice to have confirmation though. This has been opened for more than a year now with no response.

@seesharper could you please provide your insights? Is this intentional behavior (and if so, can you explain the rationale and consider updating the documentation to highlight it) or is it a bug?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants