Как я могу проверить, если тот же метод вызывается с правильными параметрами с PHPUnit и макет объекта - PullRequest
9 голосов
/ 21 ноября 2010

Я использую PHPUnit для своих модульных тестов. Я использую фиктивный объект, чтобы проверить, вызывается ли метод с правильными параметрами. Это прекрасно работает, когда я просто хочу сделать это один раз.

    $logMock = $this->getMockBuilder('Logger')
            ->disableOriginalConstructor()
            ->getMock();

    //check if it updates the correct record
    $logMock->expects($this->exactly(1))
            ->method('updateLog')
            ->with(456, 'some status');

Теперь у меня есть ситуация, которую я хочу проверить, если updateLog вызывается второй раз (с другими параметрами). Я не понимаю, как я могу сделать это с помощью метода «с».

У кого-нибудь есть предложение?

Ответы [ 4 ]

15 голосов
/ 21 ноября 2010

Я не знаю твоих насмешливых рамок. Обычно вы просто создаете другое ожидание, хотя. Я предполагаю, что это должно работать и с этим фреймворком.

$logMock->expects($this->exactly(1))
         ->method('updateLog')
         ->with(100, 'something else');

Редактировать

Кажется, что среда PHPUnit не поддерживает несколько разных ожиданий для одного и того же метода. Согласно этому сайту вы должны использовать функциональность индекса.

Тогда бы это выглядело так

$logMock->expects($this->at(0))
        ->method('updateLog')
        ->with(456, 'some status');
$logMock->expects($this->at(1))
         ->method('updateLog')
         ->with(100, 'something else');
$logMock->expects($this->exactly(2))
        ->method('updateLog');
1 голос
/ 10 июля 2015

returnCallback

Если вы не можете использовать withConsecutive(), возможно, потому что вы используете старую версию PHPUnit, у вас есть другая опция с returnCallback.

Функция returnCallback вызывается каждый раз, когда вызывается ваш фиктивный метод.Это означает, что вы можете сохранить переданные ему аргументы для последующей проверки.Например:

$actualArgs = array();

$mockDependency->expects($this->any())
    ->method('setOption')
    ->will($this->returnCallback(
        function($option, $value) use (&$actualArgs){
            $actualArgs[] = array($option, $value);
        }
    ));

$serviceUnderTest->executeMethodUnderTest();

$this->assertEquals(
    array(
        array('first arg of first call', 'second arg of first call'),
        array('first arg of second call', 'second arg of second call'),
    ),
    $actualArgs);
1 голос
/ 11 сентября 2014

Начиная с PHPUnit 4.2, вы можете использовать утверждение withConsecutive.При условии, что вы знаете порядок звонков.Ваш макет будет выглядеть так:

$logMock->expects($this->exactly(2))
        ->method('updateLog')
        ->withConsecutive(
            array(456, 'some status')
            array(100, 'something else')
        );
1 голос
/ 21 января 2012

Предыдущий ответ правильный.

Вы можете найти ответ в руководстве PHPUnit http://www.phpunit.de/manual/3.6/en/phpunit-book.html#test-doubles.mock-objects.tables.matchers поиск совпадений.Мэтчеры - это классы, возвращаемые функциями any (), never () и т. Д. ... Вам нужен PHPUnit_Framework_MockObject_Matcher_InvokedAtIndex, возвращаемый методом at ()

, вы можете найти больше, просмотрев классы PHPUnit (добавитьк пути проекта и используйте IDE, например, netbeans, чтобы перейти к ним и посмотреть, что вы можете использовать)

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...