Like many other languages, PHP is home to method chaining, a pattern that allows writing several mutators on the same object without having to name it more than once. A typical example can be found in the Zend Framework for configuration of e-mails, among other things :
$mail = new Zend_Mail();
$mail -> setBodyText('This is the text of the mail.')
-> setFrom('somebody@example.com', 'Some Sender')
-> addTo('somebody_else@example.com', 'Some Recipient')
-> setSubject('TestSubject');
This is a very simple trick that is accomplished by having every mutator return the object itself.
However, the PHP syntax rules forbid calling a member function on the result of a new-expression, so that you always require a two-step sequence: initialize the object, then call its chain of mutators.
Of course, a simple solution is to use a function:
function chain($obj) { return $obj; }
$mail = chain(new Zend_Mail())
-> setBodyText('This is the text of the mail.')
-> setFrom('somebody@example.com', 'Some Sender')
-> addTo('somebody_else@example.com', 'Some Recipient')
-> setSubject('TestSubject');
In a similar vein, there’s the matter of using the method chaining pattern on objects that were not designed for that. This is where a quick wrapper can come in handy:
// Define the appropriate class and function class WithWrapper { public $value; public function __construct($obj) { $this -> value = $obj; } public function __call($name, $args) { assert (count($args) === 1); $this -> value -> $name = $args[0]; return $this; } } function with($obj) { return new WithWrapper($obj); } // A typical record class class Person { var $age; var $firstName; var $lastName; var $married; } // Create entry for Jane $jane = with(new Person()) -> age(24) -> firstName("Jane") -> lastName("Smith") -> married(false) -> value; // Jane gets married with($jane) -> lastName("Brown") -> married(false);
This is starting to look like Visual Basic…
Recent Comments