Ich werfe hier mal ein paar Gedanken und Fragestellungen ein und hoffe, dass daraus eine Diskussion entsteht aus der man etwas lernen kann.
Wie würdet ihr eine saubere drei Schichten Architektur mit Yii umsetzen ?
Ich denke um so etwas zu realisieren, müsste man größtenteils oder ganz auf das Active Record Pattern verzichten oder ?
Findet ihr nicht auch, dass es ein wenig unsauber ist das Model, das nach der 3SA (Drei Schichten Architektur) eigentlich zur Logikschicht gehört von ActiveRecord (Datenhaltungsschicht), erben zu lassen ?
Ich denke eine Art Container-Klasse, die die Datenhaltung für das Model realisiert wäre für größere Anwendungen interessant.
Ich bin auf meiner Recherche auf Doctrine gestoßen, habe mich aber bisher noch gar nicht mit Doctrine beschäftigt. Lässt sich vielleicht in Kombination von Doctrine und Yii so etwas realisieren ?
Oder sollte man nur bei kleineren Applikationen, bei denen eine saubere Schichtentrennung nicht unbedingt von nöten ist auf Yii setzen und für größere Projekte ein anderes Framework verwenden ?
Vielleicht ist in Yii 2.0 eine sauberere Trennung angedacht ? Habe bisher aber noch nichts in der Richtung gelesen.
Erfahrungen, aber auch Gedanken und Anregungen die ihr habt sind willkommen !
Wie mbi schon sagte, gehört das ActiveRecord eindeutig zur Datenschicht. Wobei es beim MVC immer noch verschiedene Meinungen gibt, was ins Model gehört und was in den Controller gehört. Entweder macht man das Model "fat" oder den Controller. Somit sollte deine Frage erledigt sein. Yii trennt sauber!!!
Ein wenig Code, um wirklich nur eine Idee zu geben.
Natürlich völlig unausgereift, unvollständig, …
<?php
abstract class IAbstractModel extends CModel {
// CActiveRecord or something else which provides a resource. Thinking of EAV, file based storage or even a webservice.
// Change the resource without changing code in controller
protected $resourceModel;
public function __get($v) {
$this->resourceModel->$v;
parent::__get($v);
}
public function __set($v) {
$this->resourceModel->$v;
parent::__set($v);
}
public function getResourceModel() {
return $this->resourceModel();
}
// [...] //
}
?>
Die Models die im Controller angesprochen werden, würden dann von IAbstractModel erben. Weitere Methoden müssten noch in die IAbstractModel Klasse, die dann allgemeine Funktionen, beispielsweise zum finden von Instanzen definieren. Je nach Typ der Resource müssten dann die Aufrufe gemappt werden.
So kann die Resource des Models auch mal ausgetauscht werden ohne den Controller Code zu ändern. Beispielsweise eine Anwendung die "Autos" bisher in der eigenen Datenbank verwaltet hat kann die Resource gegen einen Web-Service austauschen ohne dass der Rest der Anwendung etwas davon mitbekommt. Vielleicht soll die Resource aber auch zukünftig EAV basiert sein, weil sich die Anforderungen dahingehend verändern, dass User der Anwendung Eigenschaften von "Auto" selber erweitern können soll.
Außer dem Anlegen einer zusätzlichen Model Klasse und Definieren der Resource dürfte kein großer Mehraufwand dadurch entstehen.
[Edit]
Nochmal zu den Antwortern…
mbi: Ja stimmt, ich denke auch, dass so etwas realisierbar sein sollte ohne am Framework rumzufummeln. Ich möchte einfach nur Ideen dazu sammeln und schauen ob jemand schon so etwas versucht hat. Ich traue mir das persönlich noch nicht so ganz zu, weil es doch schon ein anderes Level ist als ein fertiges Framework zu benutzen mit vorgegebenen Konventionen - was natürlich an sich eine tolle Sache ist.
speedyfw: Ja, das Active Record gehört eindeutig zur Datenschicht und genau das ist ja mein Problem.