下面的代碼段演示了緩存輸出被重構(gòu)為runPage方法的結(jié)果,它給人的感覺就像是當(dāng)用戶登錄時另一個對輸出的測試。
class PageDirectorTestCase extends UnitTestCase { // ... function TestLoggedOutContent() { $session =& new MockSession($this); $session->setReturnValue(‘get’, null, array(‘user_name’)); $session->expectOnce(‘get’, array(‘user_name’)); $page =& new PageDirector($session, new Response); $result = $this->runPage($page); $this->assertNoUnwantedPattern(‘/secret.*content/i’, $result); $this->assertWantedPattern(‘/<form.*<input[^>]*text[^>]*’ .’name.*<input[^>]*password[^>]*passwd/ims’ ,$result); $session->tally(); } function TestLoggedInContent() { $session =& new MockSession($this); $session->setReturnValue(‘get’, ‘a(chǎn)dmin’, array(‘user_name’)); $session->expectAtLeastOnce(‘get’); $page =& new PageDirector($session, new Response); $result = $this->runPage($page); $this->assertWantedPattern(‘/secret.*content/i’, $result); $this->assertNoUnwantedPattern(‘/<form.*<input[^>]*text[^>]*’ .’name.*<input[^>]*password[^>]*passwd/ims’ ,$result); $session->tally(); } function runPage(&$page) { ob_start(); $page->run(); return ob_get_clean(); } }
接下來,將加入一個檢查條件到PageDirector::run()方法來看看用戶是否已經(jīng)登錄并決定顯示什么模板:
class PageDirector { // ... function run() { if ($this->isLoggedIn()) { $this->showPage( new UserLogin($this->session->get(‘user_name’))); } else { $this->showLogin(); } $this->response->display(); } function showPage(&$user) { $vars = array( ‘name’ => $user->name() ,’self’ => SELF ); $this->response->addBodyTemplate(‘page.tpl’, $vars); } }
page.tpl看上去可能像這樣:
Welcome <?php echo $name; ?> <br>Super secret member only content here. <a href=”<?php echo $self; ?>?clear”>Logout</a>
此時,MockSession扮演了ServerStub的角色來控制決定用戶是否登錄的條件。它的功能也類似評判者,決定這個信息是否通過如下兩個途徑被正確的使用:一個是明確地被預(yù)先定義并通過tally()被驗證,另一個是不直接的生成正確的輸出,而是通過ServerStub返回的值來生成。
為了繼續(xù)重構(gòu)這段代碼,下一步要跳到前面的進(jìn)程。將要做兩個動作:清除已經(jīng)登錄的用戶和驗證登錄頁面提交的用戶名和密碼是否存在。
讓我們從注銷功能上開始:
class PageDirectorTestCase extends UnitTestCase { // ... function TestClearLoginFunctionality() { $_REQUEST[‘clear’] = null; $session =& new MockSession($this); $session->expectOnce(‘clear’, array(‘user_name’)); $session->setReturnValue(‘get’, null, array(‘user_name’)); $session->expectAtLeastOnce(‘get’); $response = new MockResponse($this); $response->expectOnce(‘redirect’, array(SELF)); $page =& new PageDirector($session, $response); $this->assertEqual(‘’, $this->runPage($page)); $response->tally(); $session->tally(); unset($_REQUEST[‘clear’]); } }
在這段代碼中,response是個偽對象,然而,一旦在Response::redirect()方法中調(diào)用了exit(),腳本將會停止執(zhí)行。由于偽對象的存在,你可以核實方法是否被調(diào)用和方法傳回了什么參數(shù),且不會產(chǎn)生任何負(fù)面影響——如腳本停止——或被實際執(zhí)行。
出處:phpchina
責(zé)任編輯:bluehearts
上一頁 php設(shè)計模式介紹之偽對象模式 [5] 下一頁 php設(shè)計模式介紹之偽對象模式 [7]
◎進(jìn)入論壇網(wǎng)絡(luò)編程版塊參加討論
|