CHAPTER 13 ■ DATABASE PATTERNS
return $obj;
}
protected function doInsert( \woo\domain\DomainObject $object ) {
print "inserting\n";
debug_print_backtrace();
$values = array( $object->getName() );
$this->insertStmt->execute( $values );
$id = self::$PDO->lastInsertId();
$object->setId( $id );
}
function update( \woo\domain\DomainObject $object ) {
print "updating\n";
$values = array( $object->getName(), $object->getId(), $object->getId() );
$this->updateStmt->execute( $values );
}
function selectStmt() {
return $this->selectStmt;
}
}
Once again, this class is stripped of some of the goodies that are still to come. Nonetheless, it does
its job. The constructor prepares some SQL statements for use later on. These could be made static and
shared across VenueMapper instances, or as described earlier, a single Mapper object could be stored in a
Registry, thereby saving the cost of repeated instantiation. These are refactorings I will leave to you!
The Mapper class implements find(), which invokes selectStmt() to acquire the prepared SELECT
statement. Assuming all goes well, Mapper invokes VenueMapper::doCreateObject(). It’s here that I use
the associative array to generate a Venue object.
From the point of view of the client, this process is simplicity itself:
$mapper = new \woo\mapper\VenueMapper();
$venue = $mapper->find( 12 );
print_r( $venue );
The print_r() method is a quick way of confirming that find() was successful. In my system (where
there is a row in the venue table with ID 12 ), the output from this fragment is as follows:
woo\domain\Venue Object
(
[name:woo\domain\Venue:private] => The Eyeball Inn
[spaces:woo\domain\Venue:private] =>
[id:woo\domain\DomainObject:private] => 12
)
The doInsert() and update() methods reverse the process established by find(). Each accepts a
DomainObject, extracts row data from it, and calls PDOStatement::execute() with the resulting
information. Notice that the doInsert() method sets an ID on the provided object. Remember that
objects are passed by reference in PHP, so the client code will see this change via its own reference.
Another thing to note is that doInsert() and update() are not really type safe. They will accept any
DomainObject subclass without complaint. You should perform an instanceof test and throw an
Exception if the wrong object is passed. This will guard against the inevitable bugs.