开发者

Dependency Injection and Unit of Work pattern

开发者 https://www.devze.com 2023-01-02 19:09 出处:网络
I have a dilemma. I\'ve used DI (read: factory) to provide core components for a homebrew ORM. The container provides database connections, DAO\'s,Mappers and their resultant Domain Objects on reques

I have a dilemma. I've used DI (read: factory) to provide core components for a homebrew ORM. The container provides database connections, DAO's,Mappers and their resultant Domain Objects on request.

Here's a basic outline of the Mappers and Domain Object classes

class Mapper{
    public function __constructor($DAO){
        $this->DAO = $DAO;
        }

    public function load($id){
        if(isset(Monitor::members[$id]){
        return Monitor::members[$id];

        $values = $this->DAO->selectStmt($id);
        //field mapping process omitted for brevity
        $Object = new Object($values);
        return $Object;
        }
    }

 class User(){
     public function setName($string){
        $this->name = $string;
        //mark modified by means fair or foul
     }
 }

The ORM also contains a class (Monitor) based on the Unit of Work pattern i.e.

class Monitor(){
    private static array modified;
    private static array dirty;
    public function markClean($class);
    public function markModified($class);
}

The ORM class itself simply co-ordinates resources extracted from the DI container. So, to instantiate a new User object:

$Container = new DI_Container;
$ORM = new ORM($Container);
$User = $ORM->load('user',1);
//at this point the container instantiates a mapper class
//and passes a database connection to it via the constructor
//the mapper then takes the second argument and loads the user with that id
$User->setName('Rumpelstiltskin');//at this point, User must mark itself as "modified"

My question is this. At the point when a user sets values on a Domain Object class, I need to mark the class as "dirty" in the Monitor class. I have one of three options as I can see it开发者_JS百科

1: Pass an instance of the Monitor class to the Domain Object. I noticed this gets marked as recursive in FirePHP - i.e. $this->Monitor->markModified($this)

2: Instantiate the Monitor directly in the Domain Object - does this break DI? 3: Make the Monitor methods static, and call them from inside the Domain Object - this breaks DI too doesn't it?

What would be your recommended course of action (other than use an existing ORM, I'm doing this for fun...)


Okay, I see. What about this:

 $user = new User;
 $monitoredUser = new Monitor( $user );

 //at update in class Monitor:
 Monitor::markDirty( $this );

Now you use the Monitor as a decorator; it adds a shell around the user object or any other object that handles incoming requests. If an object gets updated it will be marked dirty by the monitor, however because the Monitor uses a static method for this it remains within the current class scope thus avoiding recursion.


Thought i never did it, your Monitor class seems to correspond to an "Observer" design pattern. This way you don't have to ask the Monitor class to mark the class as dirty, but it should do it alone.

As i said i never did it in PHP but i'm pretty confident that you can look on Google a way to implement this design pattern in PHP.

0

精彩评论

暂无评论...
验证码 换一张
取 消