更進(jìn)一步說,你能隨心所欲的設(shè)置何種方法被調(diào)用以及調(diào)用多少次。你甚至可以驗(yàn)證那些根本不該被調(diào)用的方法。
下面是一個(gè)擴(kuò)展型的測試,它用來建立和驗(yàn)證那些復(fù)雜的設(shè)計(jì)。
class PageDirectorTestCase extends UnitTestCase { function testSomethingWhichUsesSession() { $session =& new MockSession($this); $session->setReturnValue(‘isValid’, true); $session->setReturnValue(‘get’, 1); $session->expectOnce(‘isValid’, array(‘user_id’)); $session->expectOnce(‘get’, array(‘user_id’)); $session->expectNever(‘set’); // the actual code which uses $session $session->tally(); } }
使用偽對象的原因很多,方法也多樣化。但在我們繼續(xù)前,讓我們把另外的一些類加入進(jìn)來,使其來龍去脈更加清楚。
接下來的一部分是重構(gòu)已有腳本,創(chuàng)建一個(gè)用于檢查用戶是否有相應(yīng)權(quán)限的名為UserLogin的類。
class UserLogin { var $_valid=true; var $_id; var $_name; function UserLogin($name) { switch (strtolower($name)) { case ‘a(chǎn)dmin’: $this->_id = 1; $this->_name = ‘a(chǎn)dmin’; break; default: trigger_error(“Bad user name ‘$name’”); $this->_valid=false; } } function name() { if ($this->_valid) return $this->_name; } function Validate($user_name, $password) { if (‘a(chǎn)dmin’ == strtolower($user_name) && ‘secret’ == $password) { return true; } return false; } }
(在一個(gè)實(shí)際的程序中,你應(yīng)當(dāng)按照如上所示的邏輯來查詢相應(yīng)的數(shù)據(jù)表,這種小而且編寫起來費(fèi)神的類體現(xiàn)了你將如何運(yùn)用ServerStub來組織代碼———ServerStub是一個(gè)小型的表達(dá)你想法的類,但它只是在一些限制環(huán)境下可用。)
最后一部分是創(chuàng)建響應(yīng)。為了最終在瀏覽器中顯示,我們必須處理那不斷增長的HTML內(nèi)容,如果必要的話我們也會討論HTTP重定向。(你也可以執(zhí)行其他的http頭的操作——這樣說是為了能構(gòu)隱藏它——在一個(gè)成熟的做法中,但這里使用的是一段更簡單的代碼,是為了使例子容易理解與關(guān)注。)
class Response { var $_head=’’; var $_body=’’; function addHead($content) { $this->_head .= $content; } function addBody($content) { $this->_body .= $content; } function display() { echo $this->fetch(); } function fetch() { return ‘<html>’ .’<head>’.$this->_head.’</head>’ .’<body>’.$this->_body.’</body>’ .’</html>’; } function redirect($url, $exit=true) { header(‘Location: ‘.$url); if ($exit) exit; } }
給出了這些模塊后,也是時(shí)候?qū)⑦@些新開發(fā)的、已測試的組件聚合到一個(gè)頁面中了。讓我們寫一個(gè)最終的類來協(xié)調(diào)這個(gè)頁面的所以行為,取個(gè)合適的名字PageDirector。類PageDirector具有一個(gè)很簡單的運(yùn)用程序接口:你在實(shí)例化后可以用調(diào)用它的run()方法。
這個(gè)“bootstrap”文件運(yùn)行新程序時(shí)應(yīng)如下所示:
<?php require_once ‘classes.inc.php’; define(‘SELF’, ‘http://www.example.com/path/to/page.php’); $page =& new PageDirector(new Session, new Response); $page->run(); ?>
該文件包含了所需的已定義類,并為自己定義了一個(gè)常量,給PageDirector類(其用于傳遞類Session 和類Response所依賴的實(shí)例來組成構(gòu)造函數(shù))創(chuàng)建了一個(gè)實(shí)例來執(zhí)行PageDirector::run()方法。
出處:phpchina
責(zé)任編輯:bluehearts
上一頁 php設(shè)計(jì)模式介紹之偽對象模式 [3] 下一頁 php設(shè)計(jì)模式介紹之偽對象模式 [5]
◎進(jìn)入論壇網(wǎng)絡(luò)編程版塊參加討論
|