I'm going through the zend tutorials and I am testing a class with a mock object with phpunit. When I pass a mock created from Zend\Db\TableGateway to my class, who's constructor expects a Zend\Db\TableGateway, I get an type error:
"...Argument 1 passed to Album\Model\AlbumTable::__construct() must be an instance of Zend\Db\TableGateway\TableGateway, instance of Mock_TableGateway_65b55cb0 given..."
Is this supposed happen? Are phpunit mock objects supposed to be able to "fool" the class?
Here is the real class:
class AlbumTable {
protected $tableGateway;
public function __construct(TableGateway $tableGateway) {
$this->tableGateway = $tableGateway;
}
public function fetchAll() {
$resultSet = $this->tableGateway->select();
return $resultSet;
}
public function getAlbum($id){
$id = (int) $id;
$rowset = $this->tableGateway->select(array('id' => $id));
$row = $rowset->current();
if(!$row) {
throw new \Exception("Couldn't find row: $id");
}
return $row;
}
public function saveAlbum(Album $album) {
$data = array(
'artist' => $album->artist,
'title' => $album->title,
);
$id = (int)$album->id;
if ($id == 0) {
$this->tableGateway->insert($data);
} else {
if ($this->getAlbum($id)) {
$this->tableGateway->update($data, array('id' => $id));
} else {
throw new \Exception('Form id does not exist');
}
}
}
public function deleteAlbum($id) {
$this->tableGateway->delete(array('id' => $id));
}
}
and the test:
class AlbumTableTest extends PHPUnit_Framework_TestCase {
public function testFetchAllReturnsAllAlbums() {
$resultSet = new ResultSet();
$mockTableGateway = $this->getMock('Zend\Db\TableGateway',
array('select'), array(), '', false);
$mockTableGateway->expects($this->once())
->method('select')
->with()
->will($this->returnValue($resultSet));
$albumTable = new AlbumTable($mockTableGateway);
$this->assertSame($resultSet, $albumTable->fechAll());
}
}
and the error:
Time: 102 ms, Memory: 5.00Mb
There was 1 error:
1) AlbumTest\Model\AlbumTableTest::testFetchAllReturnsAllAlbums
Argument 1 passed to Album\Model\AlbumTable::__construct() must be an instance of Zend\Db\TableGateway\TableGateway, instance of Mock_TableGateway_65b55cb0 given, called in C:\Users\MEEE\Google Drive\code\iis\www\CommunicationApp\module\Album\test\AlbumTest\Model\AlbumTableTest.php on line 20 and defined
C:\Users\MEEE\Google Drive\code\iis\www\CommunicationApp\module\Album\src\Album\Model\AlbumTable.php:9
C:\Users\MEEE\Google Drive\code\iis\www\CommunicationApp\module\Album\test\AlbumTest\Model\AlbumTableTest.php:20
FAILURES!
Tests: 4, Assertions: 9, Errors: 1.
You are not mocking the correct class. You are creating a mock of a Zend\Db\TableGateway
and you need to actually mock Zend\Db\TableGateway\TableGateway
Change you test code to:
$mockTableGateway = $this->getMock('Zend\Db\TableGateway\TableGateway',
array('select'), array(), '', false);
Your mock was failing a type-hint because your not mocking the correct class.
Mock objects will extend the class that you are mocking, so they will be an instance of the class being mocked.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With