In MVC è considerata una buona pratica avere funzioni private, non di azione, in una classe controller?

9

A volte le funzioni di azione nella classe controller possono diventare enormi e cattive, con molte linee di codice per controllare semplicemente il flusso di dati dal modello alla vista. Ad un certo punto queste enormi funzioni perdono completamente traccia dei principi di base del buon codice, cioè facendo solo una cosa, essendo piccolo, leggibile e gestibile ecc.

Sarebbe una buona pratica rompere queste enormi funzioni di azione in piccole funzioni private nella classe controller o se la necessità di tale ottimizzazione significasse che dovremmo piuttosto aggiungerle nel modello?

Voterò per avere le funzioni più piccole come private nel controller in modo che siano relative all'azione, ma ho sentito argomenti che il controller dovrebbe preferibilmente essere semplice mentre il modello può diventare enorme e scomodo; e mi stavo chiedendo quale sarebbe stato il metodo più preferito.

    
posta David 'the bald ginger' 21.05.2013 - 08:53
fonte

4 risposte

15

Potrebbe non essere la migliore analogia, ma, pensa al controller nello stesso modo in cui penseresti alla rete di un ragno. Il suo unico compito è catturare le mosche (richieste) per il ragno (strati sottostanti) da digerire. Il web può catturare e tenere mosche più piccole o più grandi (modelli). Il ruolo web di un ragno non è quello di digerire la preda, anche se può essere utilizzato a questo scopo. Più sottile e pulito è il web, più facile per il ragno guadagnarsi da vivere.

Potresti applicare in qualche modo la stessa logica alla tua applicazione MVC. Le funzioni enormi e sgradevoli che descrivi sono il comportamento più probabile del modello e dovrebbero appartenere al modello (si noti che il modello non è solo l'oggetto che viene visualizzato nella vista). Se il comportamento del modello cambia, è il modello da modificare e non il controller che lo gestisce.

Inoltre, mantenerli come metodi privati nel controller lo ingombrerebbe e lo renderebbe difficile da mantenere. Fa anche posto a una cattiva abitudine, dal momento che altre persone coinvolte nello sviluppo potrebbero essere tentate di fare lo stesso, visto che l'hanno già visto prima nel progetto.

    
risposta data 21.05.2013 - 09:27
fonte
7

La migliore risposta che posso dare è di citare il grande libro di Robert Martin, "Codice pulito" che consiglio vivamente a chiunque sia interessato all'argomento:

The first rule of functions is that they should be small. The second rule is that they should be smaller than that.

Non posso dirlo meglio. Un'altra grande citazione tratta dallo stesso libro:

Functions should do one thing. They should do it well. They should do it only.

Quando dividi il tuo codice in più funzioni, sei costretto a dare a quelle funzioni nomi significativi che possono migliorare notevolmente la leggibilità del tuo codice. Inutile dire che tutte le funzioni non destinate all'uso al di fuori della classe, dovrebbero essere private, quindi puoi facilmente riutilizzare il tuo codice via ereditarietà.

Se il tuo controller ora ha troppe funzioni, è un segno che probabilmente fa troppo. Quindi puoi dividerlo in più pezzi indipendenti o provare a spostare alcune funzioni in modelli come menzionato nell'altra risposta. Inoltre, se segui l'aroma MVC non classico, in cui le viste possono avere una certa logica, puoi inserirvi alcune delle funzioni ogni volta che si adatta.

    
risposta data 30.08.2013 - 10:59
fonte
0

In MVC cerco di assicurarmi che il mio controller sia il più "sottile" possibile e anche che i miei modelli siano il più stupidi possibile.

Le funzioni logiche e di supporto necessarie vengono inserite in classi di supporto indipendenti separate. Rende molto più semplice anche il mio test (stai testando .. giusto ??: D) I controller di test sono notoriamente difficili, ogni volta che provi a creare un'istanza di un controller per testare devi pensare al contesto HTTP e fingere http questo e quello, ed è un dolore, ma è un dolore apposta. Hai bisogno di tutto questo perché un controller è così strettamente collegato a HTTP e al web. È il punto di accesso alla tua app Web.

Le funzioni logiche e di supporto non hanno nulla a che fare con il web. Sono completamente indipendenti dall'ambiente (o dovrebbero essere). Solo questo dovrebbe dirti che non appartengono allo stesso posto. Inoltre, se leghi tutte le tue applicazioni con una logica così stretta al web, o una particolare implementazione web, non puoi mai portarla con te.

Abbiamo sviluppato il nostro sito MVC con tutte le nostre entità database (non i nostri modelli mvc, le nostre effettive entità db), il nostro archivio, le nostre classi di supporto e la nostra logica in dll indipendenti. Abbiamo avuto solo un sito Web, ma lo abbiamo fatto comunque.

Alcuni mesi fa ci è stato chiesto di creare alcune app desktop relative ad alcuni dei nostri sistemi marginali. Questo è stato fatto facilmente poiché tutto il nostro codice testato potrebbe essere facilmente riutilizzato. Se avessimo spostato il nostro codice nel nostro progetto web o inserito nei nostri controller, non saremmo mai riusciti a farlo.

    
risposta data 05.09.2013 - 10:34
fonte
-2

Oltre a Dmitri Zaitsev e agli spaziali ottime risposte non so se quanto segue è valido anche per PHP: Dovresti cercare di evitare metodi privati a causa della mancanza di possibilità di test automatici.

Sì, puoi utilizzare metaprogramming o dependency injection per testare anche i metodi privati, ma non dovresti farlo perché ha un enorme impatto sulla leggibilità del tuo codice.

Ricorda sempre il principio KISS: tienilo semplice, stupido.

    
risposta data 05.09.2013 - 14:34
fonte

Leggi altre domande sui tag