2012-04-24 14 views
3

私の問題はStrategy Pattern article in Doctrine documentationに記載されているまさにです:ドクトリン2:ページ、ブロック、Strategyパターン&関連エンティティ

  • ページエンティティ
  • ページいくつかのブロック
  • を持つことができるブロックがあるかもしれませんテキスト、画像、フォーム、カレンダー、...(戦略)
  • ページには、それが含まれているブロックを知っているが、ブロックの継承が
  • 不可能です
  • 彼らの行動について知りません

説明するソリューション(Strategyパターン)私は(詳細については記事を読む)必要まさにそうです:

ページ:

<?php 

namespace Page\Entity; 

class Page 
{ 
    /** 
    * @var int 
    * @Id @GeneratedValue 
    * @Column(type="integer") 
    */ 
    protected $id; 

    /** 
    * @var string 
    * @Column 
    */ 
    protected $title; 

    /** 
    * @var string 
    * @Column(type="text") 
    */ 
    protected $body; 

    /** 
    * @var Collection 
    * @OneToMany(targetEntity="Block", mappedBy="page") 
    */ 
    protected $blocks; 

    // ... 
} 

ブロック:

<?php 

namespace Page\Entity; 

class Block 
{ 
    /** 
    * @Id @GeneratedValue 
    * @Column(type="integer") 
    */ 
    protected $id; 

    /** 
    * @ManyToOne(targetEntity="Page", inversedBy="blocks") 
    */ 
    protected $page; 

    /** 
    * @Column 
    */ 
    protected $strategyClass; 

    /** 
    * Strategy object is instancied on postLoad by the BlockListener 
    * 
    * @var BlockStrategyInterface 
    */ 
    protected $strategyInstance; 

    // ... 

} 

戦略インタフェース:

<?php 

namespace Page\BlockStrategy; 

interface BlockStrategyInterface 
{ 
    public function setView($view); 

    public function getView(); 

    public function setBlock(Block $block); 

    public function getBlock(); 

    public function renderFrontend(); 

    public function renderBackend(); 
} 

フォームやカレンダーを表示すると、私の戦略は何かを容易に想像することができます。 私の戦略が他のエンティティのコンテンツを表示する場合はどうすればよいですか?

ブロックはエンティティクラス/ idについて知っている必要があり、関連するエンティティが削除されたときに削除する必要があります。

BlockListenerにpostLoadイベントのブロックおよびロード関連エンティティにentityClassおよびentityIdプロパティを追加すると想像しました。 しかし、関連エンティティが存在しない場合はどうなりますか?私はpostLoadのブロックを削除することはできません。

したがって、他のリスナーを作成して関連エンティティの削除を監視し、そのリスナーのブロックの参照を削除することを想像しました。

しかし、ブロックに入れることができるすべてのエンティティにリスナーを追加する必要があることを意味します。

これはうまくいくかもしれませんが、非常に複雑に思えます。

答えて

0

私はあなたの質問をよく理解しているかどうか分かりませんが、欲しいものがエンティティ内にエンティティを持ち、父親が削除されたときにそのエンティティを削除するだけであれば、エンティティをブロックとして扱い、複合パターン。

あなたは基本的には実体上の同じインターフェイスとブロックを使用することができ、およびエンティティの表示機能のようなものかもしれない

:あなたは、あなたが親エンティティを削除するとすべての子を削除するために

foreach ($block in $blocks) { 
    $block->display(); 
} 

単にエンティティのデストラクタでそれを行うことができます。

http://en.wikipedia.org/wiki/Composite_pattern:Compositeパターンの詳細について

function __destruct() { 
    foreach ($block in $blocks) { 
    /* call a common interface function that does all that need to be done, implemented on each block */ 
    } 
} 

関連する問題