0
I would like your help to solve the following problem:
Imagine that I have a Servicefactory class responsible for creating services (such as srvFact.Create<MyService>()
), a Repositoryfactory class responsible for creating repositories (such as repFact.Create<MeuRepositorio>()
). Such classes have dependencies, which I will demonstrate through the symbol A <= B
, which denotes that A depends on B. For my case I have to:
ServiceFactory <= RepositoryFactory
.
RepositoryFactory <= DbContext
.
That said, imagine that my api uses Automapper to map Viewmodels in Entity Framework Objects and that for certain mappings, it is necessary to access some repository.
What I want: I would like that given a request, as long as that request lives, any request to a Dbcontext instance, return to the same instance, to better control the Dbcontext cycle of activity. Let’s go to the code snippet:
internal void Configure(ContainerBuilder builder)
{
ConfigureContainer(builder);
Container = builder.Build();
RegisterMapping();
}
private void ConfigureContainer(ContainerBuilder builder)
{
var dbContextType = GetDbContextType();
var assembly = GetWebApiAssembly();
// (a) com essa linha o metodo 'RegisterMapping' não consegue resolver a instancia de ServiceFactory
builder.RegisterType(dbContextType).As(typeof(DbContext)).InstancePerRequest();
// (b) COM ESSA LINHA, O METODO 'RegisterMapping' consegue obter uma instancia de ServiceFactory
//builder.RegisterType(dbContextType).As(typeof(DbContext)).InstancePerRequest("myrequest");
builder.RegisterType<RepositoryFactory>().As<IRepositoryFactory>();
builder.RegisterType<ServiceFactory>().As<IServiceFactory>();
builder.RegisterApiControllers(assembly);
}
private void RegisterMapping()
{
// usando (a) no metodo 'ConfigureContainer' temos um erro:
// 'No scope with a Tag matching AutofacWebRequest'
var serviceFactory = Container.Resolve<IServiceFactory>();
Mapper.Initialize(cfg => ConfigureMapping(cfg, serviceFactory));
// usando (b) no metodo 'ConfigureContainer' conseguimos resolver ServiceFactory, porém é injetado instancias diferentes de DbContext
// o que faz com que o mapeamento dentro de 'ConfigureMapping' gere o erro:
// 'An entity object cannot be referenced by multiple instances of IEntityChangeTracker'
//using (var scope = Container.BeginLifetimeScope("myrequest"))
//{
// var serviceFactory = scope.Resolve<IServiceFactory>();
// Mapper.Initialize(cfg => ConfigureMapping(cfg, serviceFactory));
//}
}
The Method Configure(new ContainerBuilder())
is called in Global.asax: DbAccessWrapper.Init(new VaiQueConfig());
where the builder new VaiQueConfig()
calls the method Configure
passing an instance of ContainerBuilder
sorry.. I couldn’t understand what you want and what your problem is. are you giving any error? or want to "improve" the way
utiliza injeção de dependência
?– Barbetta
I’m having problems, the first is that
var serviceFactory = scope.Resolve<IServiceFactory>()
generates an error (No Scope with a Tag matching Autofacwebrequest ) if configuring the container with the linebuilder.RegisterType(dbContextType).As(typeof(DbContext)).InstancePerRequest()
;– Jesley Cáceres Marcelino
The second is that if I use the line
builder.RegisterType(dbContextType).As(typeof(DbContext)).InstancePerRequest("myrequest")
i can obtain the instance of Servicefactory, but the dependency (Repositoryfactory) injected in Servicefactory is injected with a new instance of Dbcontext, since Repositoryfactory has as dependency Dbcontext, and this generates the error (An Entity Object cannot be referenced by Multiple instances of Ientitychangetracker) when using the service in the mapping layer– Jesley Cáceres Marcelino
Come on, somebody?
– Jesley Cáceres Marcelino
Hard this case of yours, as I do not know what it is, I will comment.. if it works I answer, you already tried to do so
builder.RegisterType<SeuDbContext>().As<DbContext>();
to inject the context?– Barbetta
Yes, I will post the repository link, in case you want to simulate to understand. in general I want to build a plugin that cruds Generico, already mapping viewmodels in dto, but for that, I need a context instance only Entity by request to avoid multiple contexts errors, or errors when mult thread when context is Singleton Repository: https://github.com/Jass91/WebApiLink
– Jesley Cáceres Marcelino
Sorry, actually I can not use as you said, because I need to dynamically get the kind of class that inherits from Dbcontext, because each person could have one. ex: Meudbctx1, Odbctxdele and etc...
– Jesley Cáceres Marcelino