Search code examples
dependency-injectionentity-framework-coredryioc

Register to be created from factory


I'm trying to use DryIOC to resolve a scoped entity framework context. While this registration works, it feels weird:

container.Register<MyDbContext>( Reuse.ScopedTo<IMarkerInterface>(), Made.Of(() => Arg.Of<IDbContextFactory<MyDbContext>>().CreateDbContext()) );

Especially, Arg.Of seems to be intended to be used differently. Is there a better way to write the Made part?

I can easily register a factory for MyDbContext with the (Microsoft-DI-) ServiceCollection with AddDbContextFactory(), so I do that. Then I create the DryIOC container the rest of my application uses from the ServiceCollection with using the DryIoc.Microsoft.DependencyInjection extension.

In the DryIOC world now, I want a scoped MyDbContext. So I register the MyDbContext using ScopedTo, but I want each context instance to be produced by the previously registered (in the ServiceCollection world) factory. So, DryIOC's supposed to to resolve a factory, call create and put the result in the current scope, each time a MyDbContext is injected.

EDIT: I've upgraded to

container.Register<MyDbContext>( Reuse.ScopedTo<IMarkerInterface>(), Made.Of(container.Resolve<IDbContextFactory<MyDbContext>>(), factory => factory.CreateDbContext()) );

which is still smelly because the Resolve is unnecessary early, but feels a bit better in total.

container.Register<MyDbContext>( Reuse.ScopedTo<IMarkerInterface>(), Made.Of(() => container.Resolve<IDbContextFactory<MyDbContext>>(), factory => factory.CreateDbContext()) );

would be perfect, I guess, but doesn't work (at least with this syntax).


Solution

  • From what I understand you need something like this:

    container.RegisterDelegate<IDbContextFactory<MyDbContext>, MyDbContext>(
        factory => factory.CreateDbContext(),
        Reuse.ScopedTo<IMarkerInterface>());