簡體   English   中英

使用模擬進行單元測試(PHP)

[英]Unit testing with mocks (PHP)

我有一個類:

class Foo {
    function getCurrentBar() {
        $model = Query::findByPk($this->getSession()->get('current_bar')); // Pseudocode...

        return $model;
    }
}

所以基本上我的應用程序中一次只有一個條形,它作為整數存儲在會話中。 我經常調用一個輔助函數來查找模型實例,它會進行數據庫查詢。 還有緩存,但現在無關緊要。

我的問題是:我怎么單元測試這個 我測試的類需要這個。 我想我可以改變會話以包含id但是這意味着我需要在數據庫中有相應的模型。

最好的方法是添加方法setCurrentBar()僅用於單元測試嗎? 然后我可以模擬一個條形對象並設置它,它將用於所有單元測試。 那有意義嗎?

答案確實是依賴注入,但是你想要控制的依賴是條形的來源 ,而不是條形本身。

class Foo {
  private $query;

  function __construct($query)
  {
    $this->query = $query;
  }

  function getCurrentBar() {
    $model = $this->query->findByPk($this->getSession()->get('current_bar')); // Pseudocode...

    return $model;
  }
}

所以在您的生產代碼中

$query = new Query() // assuming findByPk() is made a normal non-static method
$realFoo = new Foo($query);

但是對於單元測試......

$testFoo = new Foo(new MockQuery());

其中MockQueryQuery類的模擬版本,它返回模擬

您也可以選擇測試部分模擬對象,直到DI系統到位為止。

class Foo {
    function getCurrentBar() {
        $model = $this->getQueryResult($this->getSession()->get('current_bar')); // Pseudocode...
        return $model;
    }
    function getQueryResult($queryParams)
    {
        return Query::findByPk($queryParams);
    }
}

然后做一個看起來有點像這樣的測試......

$myObjectToTest = $this->getMock('Foo', array('getQueryResult'), array(), '', true, true, true);
$myObjectToTest->expects($this->once())
               ->method('getQueryResult')
               ->with($whateverTheQueryParametersAre)
               ->will($this->returnValue($someResult));
$myObjectToTest->getCurrentBar();

您可以嘗試使用依賴注入

將Bar實例傳遞給Foo構造函數

class Foo
{
    private _bar;

    function __construct (Bar $bar)
    {
        $this->_bar = $bar;
    }

    public function getCurrentBar()
    {
        return $this->_bar;
    }
}

然后,您可以在運行測試時注入模擬Bar對象。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM