2012-04-23 1 views
6

Sto scrivendo il mio framework MVC in PHP, solo per scopi di apprendimento. Non è stato davvero difficile avere una classe router/dispatcher per chiamare il controller/azione giusto, ecc.Un BaseModel in PHP MVC, buono o cattivo?

Ma ora sono nella parte in cui userò i modelli. O in realtà, il livello del modello. Ma c'è qualcosa che mi confonde.

Un sacco di altri framework MVC ha un 'BaseModel'. Ho letto che questo è in realtà una cattiva pratica, perché il "Modello" non dovrebbe essere visto come un'altra classe. Ma come un vero 'strato', che può contenere cose come il pattern 'mapper' o il pattern 'repository' ecc.

Ma a dire il vero, non vedo alcun vantaggio in questo. Per me, una classe 'BaseModel' sembra essere il modo più veloce per andare, con gli stessi risultati.

posso semplicemente fare qualcosa di simile:

class User extends BaseModel 
{ 
    // the GetUserBy* could easily be something that's handled by the 
    // BaseModel class, like in the Repo pattern. 

    public function getUserByName ($name) 
    { 
     // no error handling of any kind, just for simplicity 
     return $this->db->exec("SELECT * FROM users WHERE name='".$name."'"); 
    } 

    // $data = array 
    public function saveUser ($data) 
    { 
     // Make sure no extra fields are added to the array 
     $user = array ('name' => $data['name'], 
         'address' => $data['address']); 

     $this->db->autoSave ($user); 
    } 
} 

Ma se mi piacerebbe andare per un modello di repository poi devo creare i seguenti: Repositories Enti DAO

Entità hanno Aggregati alla altri repository. Quindi in pratica sto scrivendo manualmente tutto il mio schema di database sugli oggetti ...

Alla fine, qual è la differenza ??? Tranne che probabilmente avrei potuto risparmiare un sacco di tempo semplicemente usando una classe BaseModel ...

Ma perché è ancora considerata una cosa negativa allora ?? Non è che il modello di pronti contro termine disaccoppia la mia applicazione più di quanto sto facendo ora. Perché per me, quei modelli di cui sopra sembrano essere molto sopravvalutati. Probabilmente funzionerebbe solo in un'applicazione che ha uno stato condiviso; Salva gli oggetti localmente (nel repository) e li impegni in seguito.

è per questo che penso che nessuno può realmente rispondere a questa ...

ma sto ancora sperando di vedere una risposta decente che mi fa andare: "ahhhh ... cosa stavo pensando .... ". Ma se no, allora sono sicuro del mio caso che il BaseModel non è affatto un male e che la maggior parte dei blogger sono solo un gruppo di pecore :-)

+1

sembra carino [Propel] (http://www.propelorm.org/) -ish – Alp

+2

Puoi darci un link a uno di questi post del blog? – webbiedave

+1

@Alp l'esempio di codice? Propel è solo un ORM, non sto andando in quella direzione, perché mi piace scrivere query personalmente. Non mi riferisco agli ORM. Ma preferisco non usarli neanche. Un po 'di magia è ok, ma non troppo. Ma questa è tutta un'altra storia. – Vivendi

risposta

1

Non è che il modello di pronti contro termine disaccoppia la mia applicazione più quindi sto facendo

L'applicazione è strettamente accoppiati a componenti di database SQL (che sono, in effetti, in qualità di vostro mapper) . Tuttavia, nonostante questo, il tuo design è molto più simile a un Repository di un approccio Active Record (che è probabilmente ciò di cui la maggior parte di questi blogger di cui fai riferimento si aggrappano).

record attivi racchiudono non solo i dati, ma anche l'accesso al database:

$user = new User(); 
$user->setUsername('jane'); 
$user->setEmail('[email protected]'); 
$user->save(); 

E 'bello avere gli oggetti record di essere a conoscenza del strato di persistenza (separazione degli interessi). La tua "base" fa proprio questo restituendo array di dati utente e quando questi array vengono modificati, devono essere restituiti all'utente "base" per il salvataggio. Puoi cambiare la tua denominazione in:

class UserRepo extends BaseRepo 
{ 
    // user-specific repo code... 
} 

$userRepo = $this->getRepo('User'); 
$user = $userRepo->getUserByName('jane'); 
$user['email'] = '[email protected]'; 
$userRepo->save($user); 

Non c'è niente di sbagliato nell'avere un repository di base.

+0

Immagino che tu abbia ragione. Assomiglia ad un pattern Repo in qualche modo. Ma non sto usando alcuna classe di entità o oggetti valore.Come ho anche detto nel mio post, sembra molto riscrivibile lo schema del database in "oggetti". --- Il mio 'UserRepo' restituisce semplicemente gli array presi direttamente dalle query SQL. Non vedo l'uso di Entità/VO. Perché se usassi le Entità, sto praticamente dicendo, dammi i miei risultati come una matrice dalla mia query, mappali al mio oggetto Entity e usali per ottenere/impostare i dati. Non vedo perché dovrei perdere tempo in questo (Entità). Qualche idea su quello ...? – Vivendi

+0

Mappare i tuoi record su oggetti permette loro tutte le opzioni di OOP se desideri (una struttura definita, interfacce, tipo di suggerimento, ecc ...). La matrice basata è più veloce, utilizza meno risorse e sei in grado di passarle alle funzioni di array PHP nativi. È un trade-off ed è totalmente una tua chiamata. – webbiedave

0

La classe Model dovrebbe essere astratta, solo i metodi di definizione senza implementarli. Per quanto riguarda il modello User, è possibile scrivere facilmente un'interfaccia GettingUsers che avrebbe tutte queste funzioni e implementarla nel modello User.

+2

questa è una risposta molto riservata e nessuna affermazione è seguita da una spiegazione decente per quale motivo. Inoltre, se la classe del modello definisce solo i metodi senza alcuna logica di implementazione, allora dovrebbe essere un'interfaccia, non astratta. come ho detto, ho potuto "facilmente" separarlo in modelli, classi astratte, interfacce. ma * qual è * il vantaggio contrario al solo BaseModel. Sembra che tu non abbia nemmeno provato a rispondere. – Vivendi

+1

@Vivendi - domanda interessante, ma per favore sii civile. La verità è in giro da un po ', come dimostra il rappresentante, e tu sei nuovo qui. – halfer

+1

@halfer Spiacente, spero che nessuno abbia offeso la mia risposta. Non volevo essere scortese in ogni caso. Avrei dovuto inserire alcune cose nel mio commento in un modo diverso. – Vivendi

0

Non utilizzerei affatto un modello di base poiché la maggior parte dei modelli non ha un'interfaccia uniforme a cui devono essere conformi. È possibile creare una classe base per un numero di diversi tipi di modelli (che è solo una programmazione di base orientata agli oggetti), se lo si desidera.

Nel complesso, credo che i modelli siano i componenti "allentati" che si collegano con un controller e si visualizzano con una o più viste. Non possono avere un'interfaccia uniforme perché tutti farebbero cose diverse: alcuni potrebbero non parlare nemmeno con un archivio di persistenza, alcuni potrebbero non essere persistenti e/o alcuni potrebbero essere composti da altri modelli.

1

Se stai cercando di imparare buone pratiche MVC dai framework PHP, allora stai sbagliando. Anche i migliori framework in PHP sono pieni di errori e difetti di progettazione.

I framework che hanno "BaseModel" di solito implementano una sorta di ORM. E il modello più popolare qui è ActiveRecord. È bello per le tabelle semplici, senza relazioni con gli altri (fondamentalmente - getter/setter glorificati). Ma inizia a crollare, quando si tratta di strutture e interrogazioni più complesse. Di solito causando un esteso technical debt.

L'altro motivo, perché questo approccio causa problemi, s è che anche il tuo "modello" in questo caso ha delle responsabilità. La logica di business è strettamente legata allo storage e lo storage è saldato alla logica. Man mano che l'applicazione cresce, tali "modelli" accumulano hack.

E no, il "gruppo di blogger" non sono pecore. Hanno appena letto libri sull'architettura dell'applicazione e sulla programmazione orientata agli oggetti. Quando è stata l'ultima volta che hai letto un libro su questo argomento?

+0

Sto leggendo molte cose contraddittorie :). Ma come lo faresti in modo da non accumulare così tanto nel modello? Sembra che tu abbia o meno modelli grassi, controller grassi, una libreria da qualche parte, stored procedure e così via. cosa fai? Devo evitare le idee di ActiveRecord a causa di molte query complesse. AR si sente come un hack e diventa enorme. Mi piace anche SQL, che poi mi accoppia strettamente. Grazie. – johnny

+0

@johnny Penso che i tuoi problemi principali derivino dall'avere cattive informazioni su cosa sia in realtà "modello". Forse [questo post] (http://stackoverflow.com/a/5864000/727208) aiuta un po '. –