❔ Getting all instances from a IServiceScope

I have a callback system that I want to ensure all subscribers are removed from when a dependency scope is destroyed. To achive this I want to itterate over all instanciated class and unregister them. But I am struggeling with getting all created instances from the IServiceScope. I cant cast to ServiceProviderEngineScope, as that is a sealed internal class. How does one normally access this information?
12 Replies
Sossenbinder
Sossenbinder16mo ago
You could have the affected classes inherit from IDisposable If a scope is disposed, it will dispose all the disposables inside as well
Ole (ping please)
Ole (ping please)OP16mo ago
That was my frist thought, but then I need to store the event subscriber class so I can call it from dispose. I never need it outside of dispose and the construtor so it would be kind of neat to have a void Unregister(EventHub hub) function in a interface
Sossenbinder
Sossenbinder16mo ago
Ah What could also work: Register your services towards an interface containing your method And then you can resolve IEnumerable<IInterface> That will resolve all instances registered for that interface
Ole (ping please)
Ole (ping please)OP16mo ago
But that has the potential to be very inefficient? For a given scope there might be 500 potential classes, but depending on the incomming request, the path taken might only instanciate 5. Doing it that way will force the instanciation of all.
Sossenbinder
Sossenbinder16mo ago
Oh, I see now, so you want to get the "alive" objects. I'm not sure if there's a way to do this with MS DI, I know Autofac etc. have interceptor features. I guess with MS DI you would have to have some kind of tracker service injected into all others Not sure if there's a way to write an interceptor around ServiceProvider
Ole (ping please)
Ole (ping please)OP16mo ago
I cant find a way of doing it, which is a bit strange. I agree its a bit of a corner case but it cant be that unusual. Would be good for some logging cases as well I would assume
Unknown User
Unknown User16mo ago
Message Not Public
Sign In & Join Server To View
Ole (ping please)
Ole (ping please)OP16mo ago
Because it requires me to store the variable. It means I would have to write something like this:
class MyClass : IDisposable
{
EventHub _hub;

public MyClass(EventHub hub)
{
_hub = hub;
_hub.Subscribe<ItemSaved>(this, OnSaved);
}

public void Dispose() => _hub.Remove(this);
}
class MyClass : IDisposable
{
EventHub _hub;

public MyClass(EventHub hub)
{
_hub = hub;
_hub.Subscribe<ItemSaved>(this, OnSaved);
}

public void Dispose() => _hub.Remove(this);
}
but what I really want is the following, as I never need the hub outside of create/delete
class MyClass : IDisposable
{
public MyClass(EventHub hub)
{
hub.Subscribe<ItemSaved>(this, OnSaved);
}

public void Unsub(EventHub hub) => hub.Remove(this);
}
class MyClass : IDisposable
{
public MyClass(EventHub hub)
{
hub.Subscribe<ItemSaved>(this, OnSaved);
}

public void Unsub(EventHub hub) => hub.Remove(this);
}
Sossenbinder
Sossenbinder16mo ago
You could have your .Subscribe return a delegate which you can store and simply invoke in your dispose So your Subscribe would return a self-cleanup callback If that would make this cleaner But it essentially only removes the need for a _hub = hub Otherwise, the best I can come up with on the spot would be a base class tracking the disposables
Mayor McCheese
Mayor McCheese16mo ago
I believe the sample I sent you includes method to do what you are trying to accomplish; of course you'll need to adapt to your circumstances however.
Accord
Accord16mo ago
Was this issue resolved? If so, run /close - otherwise I will mark this as stale and this post will be archived until there is new activity.
Want results from more Discord servers?
Add your server