Ciao Sto usando un contenitore IoC e vorrei inizializzare un servizio (una parte del quale implica un "lavoro pesante" che comunica con un database) all'interno il costruttore.IoC Initialize Service con lavori pesanti nel costruttore ma evitando un metodo Init() temporale
Questo particolare servizio memorizza le informazioni che vengono rilevate da un servizio di iniezione IPluginToServiceProviderBridge
, queste informazioni vengono salvate nel database tramite UnitOfWork
.
Una volta eseguito il boot, i controller con comandi e servizi con gestori vengono utilizzati per tutte le altre interazioni. Tutti i comandi sono racchiusi all'interno di un ambito di vita, quindi il salvataggio e lo smaltimento di UnitOfWork
vengono eseguiti dal gestore e non dal servizio (questo è ottimo per il codice pulito).
La stessa pulizia e separazione degli interessi per il risparmio e le transazioni non si applica per la Initializer
all'interno del servizio come tutto si svolge nel costruttore:
public PluginManagerService(
IPluginToServiceProviderBridge serviceProvider,
IUnitOfWork unitOfWork)
{
this.unitOfWork = unitOfWork;
this.serviceProvider = serviceProvider;
lock (threadLock)
{
if (initialised == false)
{
LinkPluginsWithDatabase();
initialised = true;
}
// I don't like this next line, but
// not sure what else to do
this.UnitOfWork.Save();
}
}
protected void LinkPluginsWithDatabase()
{
var plugins =
this.serviceProvider.GetAllPlugins();
foreach (var plugin in plugins)
{
var db = new PluginRecord
{
interfaceType = plugin.InterfaceType;
var id = plugin.Id;
var version = plugin.Version;
}
// store in db via unit of work repository
this.unitOfWork.PluginsRepository.Add(db);
}
}
Un paio di punti:
Idealmente mi voglio evitare di usare una fabbrica perché complica la gestione della vita dell'ottica, sarei felice di refactoring per una separazione migliore se sapessi come.
Voglio davvero evitare di avere un metodo separato Init()
per il servizio, mentre consentirebbe la transazione e il salvataggio tramite comando/gestore, sarebbe richiesto un sacco di codice di controllo e credo che ciò introdurrebbe anche problemi temporali.
Considerato quanto sopra, è accettabile chiamare il UnitOfWork.Save()
all'interno del mio costruttore o potrei refactoring per un codice più pulito e una migliore separazione?
I concordano evitando il metodo Init(). odori di troppa responsabilità per un singolo oggetto. la fabbrica è la strada da percorrere qui. il concetto comunque. dovresti evitare questo tipo di lavoro nel ctor di un oggetto.se riesci a gestire l'ambito dell'oggetto, come può complicare una fabbrica? –