2016-06-01 2 views
1

私はMVCプロジェクトのデータマッパーパターンを実装しようとしています。私はこれが以前に尋ねられたことを知っていますが、私が正しい方向に動いているかどうかまだ分かりません。PHP MVCでデータマッパーパターンを実装する方法

コントローラ

mywebsite.com/dashboard/index上のユーザの土地を、イベントログデータベースからイベントのリストを表示するために取得します。私は、右下の私のコントローラ、DataMapperのとドメインオブジェクト/エンティティのコードを貼り付けました表。 index()関数は、Datamapperインスタンスを作成し、データベースラッパーを渡します。次に、データマッパーからデータをフェッチしてHTMLテーブルを動的に生成します。

class DashboardController extends BaseController { 
    public function index() { 
     require_once '../app/domain/mappers/EventMapper.php'; 
     require_once '../app/include/HTMLTableCreator.php'; 

     try { 
      $eventMapper = new EventMapper(new Database('db')); 
      $table = new HTMLTableCreator($eventMapper->findByLimit(20)); 
     } catch (DatabaseException $e) { 

     } 

     $this->view('/home/dashboard', ['table' => $table->toString()]); 
    } 
} 

DataMapperの

このクラスは、データベースからの最後の20個のログイベントを取得するためのfindByLimit()メソッドが含まれています。 fetchCollection()メソッドはドメインエンティティにデータを取り込み、配列に収集してコントローラに戻します。

SQLクエリが複数の行(=複数のドメインオブジェクト)を返すときに、複数のデータマッパーで使用するジェネリックコレクション関数を作成する必要がありますか?また、データマッパーで任意のタイプのデータソースを使用できますか?

require_once '../app/domain/entities/Event.php'; 
require_once '../app/domain/interfaces/EventMapperInterface.php'; 

/** 
* EventMapper class 
*/ 
class EventMapper implements EventMapperInterface { 

    protected $dbh; 
    protected $elements; 

    public function __construct(Database $dbh) { 
     $this->dbh = $dbh; 
    } 

    public function fetchCollection($objects) { 
     foreach($objects as $object) { 
      $event = new Event(); 
      $event->setId($object['id']); 
      $event->setDateTime($object['datetime']); 
      $event->setMessage($object['message']); 
      $event->setHostname($object['hostname']); 

      $this->elements[] = $event; 
     } 

     return $this->elements; 
    } 

    public function findByLimit($limit = 20) { 
     $events = $this->dbh->sql_select('SELECT * FROM eventlog LIMIT ' . $limit, []); 

     return $this->fetchCollection($events); 
    } 
} 

ドメインオブジェクト/エンティティ

いくつかの単純なゲッターとセッターとの最後のドメインオブジェクトで。これはドメインオブジェクトのプロパティの検証を行う場所ですか?

class Event { 

    protected $id; 
    protected $dateTime; 
    protected $message; 
    protected $hostname; 

    public function setId($id) { 
     $this->id = $id; 
    } 

    public function getId() { 
     return $this->id; 
    } 

    public function setDateTime($dateTime) { 
     $this->dateTime = $dateTime; 
    } 

    public function getDateTime() { 
     return $this->dateTime; 
    } 

    // rest omitted for clarity 
} 

私の実装で何か不足していますか?

+0

仕様は不明です。あなたが欠けているものを言うのは難しいです。私は自分のものを転がすのではなく、いくつかの既存のORMの実装を見ていきます:) –

+0

@ЯрославРахматуллин私は反対です。ほとんどのORM実装は過度のものになりました。 ORMはそれらのすべてを同等に良い、ほんのわずかしか行うことはできません。 – dbf

+0

ええ、私は複雑なORMの実装は必要ありません。他のフレームワーク/実装から学び、自分のものを少し書くことで、私は最も学びます。 – Beeelze

答えて

0

SQLクエリが複数の行(=複数のドメインオブジェクト)を返すときに、複数のデータマッパーで使用するジェネリックコレクション関数を作成する必要がありますか?

いいえobectsのプロパティがdbテーブルの列で1 = 1である場合は、既存の方法を使用してください。例えばPDO-FETCH-CLASS。とにかく、エンティティごとに1つのマッパーを持つ方がクリーンです。非常に一般的な場合は、「スーパー」マッパーを使用します。

データマッパーで任意のタイプのデータソースを使用できますか?

DataSourceがある種のコレクション読み書きインタフェースであると仮定すると、確かに。​​があり、これは__construct(DataSource $ds)で置き換えられます。

その他の注意事項:データベースとマッパーサービスをコントローラに注入してください。

+0

私はPDOの代わりにmysqliを使用していますが、おそらくそれを調べるべきです。そして、私はコントローラのコンストラクタを使ってデータベースとマッパーサービスを注入するでしょうか?次に、そのコントローラー内のすべてのアクションメソッドに、そのマッパーが必要であると仮定する必要があります。このマッパーは、Single Responsibility原則に適用されます。 – Beeelze

+0

既存のIoCコンテナを見ることをお勧めしますか?私は周りを見回していくつかの実装を見つけました。私はそのようなコンテナをどこに初期化するのかはわかりませんが、それは私が考える別の問題です。 – Beeelze

関連する問題