Iniezione di dipendenza: A che punto posso creare un nuovo oggetto?

11

Sto refactoring di un'applicazione PHP , e sto cercando di fare ha molto dependency injection (DI) possibile.

Mi sento come se avessi una buona conoscenza di come funziona, e posso certamente vedere le mie classi diventare molto più snelle e robuste.

Sto refactoring in modo da poter iniettare una dipendenza piuttosto che creare un nuovo oggetto all'interno della classe, ma a un certo punto dovrò creare alcuni oggetti, cioè usare la temuta new keyword.

Il problema in cui mi sono imbattuto ora è a che punto posso effettivamente creare nuovi oggetti? Sembra che finirò in una classe di alto livello, creando un sacco di nuovi oggetti in quanto non ci sono altri posti dove andare. Questo sembra sbagliato.

Ho letto alcuni blog che utilizzano classi di fabbrica per creare tutti gli oggetti, e quindi si inserisce la fabbrica in altre classi. Puoi quindi chiamare i metodi di fabbrica e la fabbrica crea il nuovo oggetto per te.

La mia preoccupazione per questo è ora che le mie classi di produzione saranno un new free-for-all! Immagino che questo possa essere OK in quanto sono classi di fabbrica, ma ci sono alcune regole su cui attenersi quando si usano modelli di fabbrica e DI, o sto andando fuori strada qui?

    
posta Gaz_Edge 31.10.2013 - 19:14
fonte

3 risposte

10

Dopo un po 'di ricerche su google per questo, sembra che (come menzionato in un commento sopra) la classe di livello superiore di cui stavo parlando sia chiamata Composition Root .

Sembra davvero essere la soluzione accettata per aggiungere la creazione di tutti gli oggetti all'interno di questa Composition Root (o fare riferimento a un contenitore IoC da qui).

La mia preoccupazione iniziale era che questa classe di alto livello finisse per essere un po 'confusa. Questo è vero in una certa misura, ma i pro fuori pesano i contro. Ad esempio, posso vedere la leggibilità, la testabilità e la manutenibilità di tutte le altre mie classi è migliorata.

La classe di primo livello potrebbe essere un po 'caotica, piena di new e set_property() ma devo dire che in realtà preferisco avere tutto questo codice in un posto, piuttosto che sparsi per tutte le altre classi

Un'altra pagina utile che discute i risultati delle prestazioni di questo metodo qui

    
risposta data 06.11.2013 - 09:49
fonte
3

Una classe factory avrà new sparsa per tutto il tempo. Sarebbe la creazione di qualsiasi oggetto che si sta richiedendo e probabilmente le dipendenze di tale oggetto. Poiché il lavoro delle fabbriche consiste nel creare un'istanza dell'oggetto corretto per te che hai new in questa classe non è una cosa negativa.

DI è tale da avere un design liberamente accoppiato. È possibile apportare modifiche all'applicazione modificando la dipendenza fornita a ciascun oggetto. Rendi la tua applicazione flessibile, estensibile e facile da testare.

Al livello più alto, avrai un codice che istanzia un paio di fabbriche, configura le connessioni ai servizi e invia una risposta. Avrà una buona quantità di new o chiamate statiche per istanziare gli oggetti che sono necessari per la tua applicazione. Quello sarebbe dove questo appartiene.

    
risposta data 31.10.2013 - 22:45
fonte
-2

I miei due centesimi qui:

I am refactoring a php application and I am trying to do has much dependency injection as possible

Non si specifica se si sta utilizzando un'infrastruttura per le dipendenze. Penso che dovresti assolutamente. Usa qualcosa che ti offre le funzionalità di cui hai bisogno: link .

The problem I have now run into is at what point can I actually create new objects? Its looking like I'll end up at a top level class, creating loads of new objects as there is no where else to go. This feels wrong.

Normalmente usi la configurazione o un punto centrale per l'istanziazione degli oggetti iniziali che compongono la tua applicazione. Il contenitore creerà gli oggetti per te.

Quindi accedi agli oggetti (servizi, provider, controllori ...) tramite il contenitore IoC. Creerà in modo trasparente un oggetto per te, se necessario, o ti fornirà un riferimento all'istanza esistente appropriata.

Naturalmente, all'interno della tua particolare implementazione di oggetti puoi istanziare altri oggetti su cui non hai bisogno DI (strutture dati, tipi personalizzati, ecc.), ma è normale programmazione.

I've read some blogs that use factory classes to create all the objects, and then you inject the factory into other classes. You can then call the factory methods, and the factory creates the new object for you.

Normalmente, usi una Fabbrica se vuoi che la struttura IoC istanzia da alcuni oggetti IoC attraverso le tue fabbriche (questo è necessario quando l'istanziazione di un particolare oggetto richiede un lavoro extra). Se puoi semplicemente creare i tuoi oggetti con "nuovo oggetto ()" e impostando alcune proprietà, non devi necessariamente utilizzare un modello di fabbrica.

In altre parole, direi che l'utilizzo di un pattern Factory per una classe o un gruppo di classi dipende da come si desidera modellare tali classi, non dal fatto che si utilizzi DI (a meno che l'implementazione DI richieda esplicitamente le fabbriche, che è insolito).

Configura anche il tuo framework IoC per usare una Factory quando usi una lib di terze parti che già richiede l'uso di una Factory. In questo caso non hai alcun controllo su questo e devi dire al tuo contenitore IoC: "hey, quando chiedo una di queste interfacce, devi usare questa fabbrica per fornirmi un'istanza appropriata".

My concern with doing this is now my factory classes are going to be a new free-for-all! I guess this may be ok as they are factory classes, but are there some rules to stick to when using factory pattern and DI, or am I going way off the mark here.

In questo caso, sembra che non sia necessario utilizzare modelli di fabbrica per questi oggetti / servizi / controller / qualsiasi cosa, e puoi semplicemente configurare il tuo IoC per creare un'istanza con "nuova" la classe appropriata e iniettare tutto il resto.

Spero che aiuti.

    
risposta data 31.10.2013 - 19:27
fonte

Leggi altre domande sui tag