2010-11-19 7 views
2

Ich versuche herauszufinden, wie Domain-Modelle in verschiedenen Teilen der Anwendung wiederverwenden und ich habe das Gefühl, dass das Data Mapper-Muster der Weg ist. Das folgende Beispiel enthält Methoden, die direkt auf die Methoden des Mappers zugreifen.Domain-Objekt, das mehr als einen Data Mapper benötigt

class Groups 
{ 
    protected $_groups = array(); 

    public function addGroup($name) 
    { 
     $this->_groups[] = $name; 
    } 

    public function doSomethingGroupy($cakes) 
    { 
     // get all the groups that have cake 
     return $cakeyGroups; 
    } 
} 

... Und ein Mapper die Methoden der Groups-Klasse zu entsprechen.

class GroupMapper 
{ 
    public function find($id, Groups $group) 
    { 
     // Mappy type things, maybe some sql 
    } 

    public function fetchByNeediness($cuddles, Groups $group) 
    { 
     // More mappy type things 
    } 

    public function save(Groups $groups) 
    { 
     // Saves 
    } 
} 

Allerdings, wenn irgendwann später habe ich die gleichen Gruppen Modelle verwenden wollten, aber die Gruppen mit verschiedenen Abfragen füllen würde ich einen anderen Mapper verwenden.

class AngryGroupMapper 
{ 
    public function find($id, Groups $group) 
    { 
     // Something similar but with other tables and joins 
    } 

    public function fetchByRage($anger, Groups $group) 
    { 
     // Something new but only needed here 
    } 

    public function isEditable(Groups $groups) 
    { 
     // Do some querying 
     return $bool; 
    { 
} 

Jetzt kenne ich das Ziel dünnen Controller ist - Fat Model, so hätte ich ein anderes Modell die Mapper Karte (sozusagen) an das Modell?

class FatModelRepository 
{ 
    public function getHappyGroups() 
    { 
     $mapper = new GroupMapper(); 
     return $mapper->fetchByNeediness('Puffy Shoes', new Groups()); 
    } 

    public function getSadGroups() 
    { 
     $mapper = new AngryGroupMapper(); 
     return $mapper->fetchByRage('Aghh!', new Groups()); 
    { 

    public function save(Groups $groups) 
    { 
     $mapper = new GroupMapper(); 
     return $mapper->save($groups); 
    { 
} 

Antwort

4

Das Datenmodell sollte keine Kenntnis vom Data Mapper haben. Ihre Groups-Klasse/Ihr Modell sollte keine Suchmethoden haben und keinen Zugriff auf den Mapper haben.

Sobald Sie die Mapper-Abhängigkeit von Ihrem Modell entfernen, werden Ihre Probleme verschwinden.

HINWEIS: Check Doctrine 2

+0

Was ist, wenn "Gruppen" eine Sammlung ist, die "Gruppen" -Objekte enthält und diese selbst Modelle sind, die eine abhängige Zuordnung erfordern. Müsstest du sie von Gruppen lösen, sie durch einen Mapper leiten und sie dann wieder an die Sammlung anhängen? Bedeutet das, dass der Kunde/Controller Kenntnisse der Mapper benötigt? – gawpertron

+0

Ihr 'FatModel' wird als Repository bezeichnet. Es gibt eine gute Erklärung dafür hier: http://msdn.microsoft.com/en-us/magazine/dd569757.aspx#id0400058 – rojoca

+0

Warum würden Sie? Entwerfen Sie es nach Ihren Bedürfnissen. Ich würde kein Repo als Cache verwenden. Setzen Sie den Cache auf den Data Mapper. – rojoca

0

out Wie rojoca sagt, Sie sollten nicht den Abruf haben/finden Methoden direkt auf dem Modell. Technisch hat er auch recht, dass das Modell keinen Verweis auf den Mapper speichert, aber in weniger komplexen Situationen halte ich das für in Ordnung, solange das Modell nur die abstrakteste Form des Mappers enthält, die Sie planen (zB eine Art Basis-Mapper) Klasse oder eine Schnittstelle).

Angesichts der Dinge, sollten Sie nur Methoden zum Mapper hinzufügen, und dafür würde ich nur Vererbung, dh verwenden. Erweitern Sie Ihren Gruppen-Mapper für die neue Funktionalität. Dies erfordert natürlich, dass der Mapper in das Modell injizierbar ist. Aber wenn Sie möchten, dass das Modell einen Verweis auf seinen Mapper enthält, muss es trotzdem injizierbar sein.

+0

Bei meinen ersten Versuchen fügte ich einen Verweis auf den Mapper hinzu und erkannte schon früh die Grenzen, die sich dabei ergeben. Aber ich kann mir nicht vorstellen, wie Mapper zu verwenden sind, ohne dass ein Model oder ein Controller sich dessen bewusst ist? – gawpertron

+0

Ich denke, es ist etwas falsch mit Ihren Controllern mit den Mappern direkt, da die Controller anwendungs-/modulspezifisch sind. – prodigitalson

+0

Kann ein Mapper von einem anderen Mapper wissen? – gawpertron