У меня есть несколько сервисов, каждый из которых имеет UnitOfWork
, внедренный в конструктор с помощью Simple InjectorIoC. контейнер.
В настоящее время я вижу, что каждый экземпляр UnitOfWork
является отдельным объектом, это плохо, поскольку я использую Entity Framework и требую одинаковую контекстную ссылку для всех единиц работы.
Как обеспечить внедрение одного и того же экземпляра UnitOfWork
во все службы при каждом запросе разрешения? Мой UnitOfWor
будет сохранен декоратором внешнего обработчика команд после завершения команды.
Обратите внимание, что это общая библиотека, которая будет использоваться как для MVC, так и для Windows Forms. Было бы неплохо иметь универсальное решение для обеих платформ, если это возможно.
Код ниже:
// snippet of code that registers types
void RegisterTypes()
{
// register general unit of work class for use by majority of service layers
container.Register();
// provide a factory for singleton classes to create their own units of work
// at will
container.RegisterSingle();
// register logger
container.RegisterSingle();
// register all generic command handlers
container.RegisterManyForOpenGeneric(typeof(ICommandHandler<>),
AppDomain.CurrentDomain.GetAssemblies());
container.RegisterDecorator(typeof(ICommandHandler<>),
typeof(TransactionCommandHandlerDecorator<>));
// register services that will be used by command handlers
container.Register();
container.Register();
}
Желаемый результат строки ниже — создать объект, который имеет общий экземпляр UnitOfWork во всем построенном графе объектов:
var handler = Resolve>();
Вот мои сервисы:
public class PluginManagerService : IPluginSettingsService
{
public PluginManagerService(IUnitOfWork unitOfWork)
{
this.unitOfWork = unitOfWork;
}
private readonly unitOfWork;
void IPluginSettingsService.RegisterPlugins()
{
// manipulate the unit of work
}
}
public class SynchronisationService : ISynchronisationService
{
public PluginManagerService(IUnitOfWork unitOfWork)
{
this.unitOfWork = unitOfWork;
}
private readonly unitOfWork;
void ISynchronisationService.SyncData()
{
// manipulate the unit of work
}
}
public class SyncExternalDataCommandHandler
: ICommandHandler
{
ILogger logger;
ISynchronisationService synchronisationService;
IPluginManagerService pluginManagerService;
public SyncExternalDataCommandHandler(
ISynchronisationService synchronisationService,
IPluginManagerService pluginManagerService,
ILogger logger)
{
this.synchronisationService = synchronisationService;
this.pluginManagerService = pluginManagerService;
this.logger = logger;
}
public void Handle(SyncExternalDataCommand command)
{
// here i will call both services functions, however as of now each
// has a different UnitOfWork reference internally, we need them to
// be common.
this.synchronisationService.SyncData();
this.pluginManagerService.RegisterPlugins();
}
}