Вызовы деструктора тестирования GMock

Я прочитал раздел в поваренной книге gmock, посвященный насмешливым деструкторам, но я Мне не повезло заставить его работать. Мой код почти точно соответствует тому, что говорит документ:

class MockFoo : public Foo {
public:
    MockFoo() {}
    MOCK_METHOD0(destroyMockFoo, void());
    virtual ~MockFoo() { destroyMockFoo(); }
};

TEST_F(DestructorTest, shouldFail) {
    MockFoo* foo = new MockFoo();
    EXPECT_CALL(*foo, destroyMockFoo());
}

Но когда я запускаю код, тест проходит без ошибок. Я получаю сообщение об ошибке в конце тестового вывода об утечке объекта:

DestructorTest.cpp:149: ERROR: this mock object (used in test DestructorTest.shouldFail) should be deleted but never is. Its address is @0x8178790.
ERROR: 1 leaked mock object found at program exit.

но это не то, что я хочу, и это не то, что, по словам доктора, должно произойти.

Так что я делаю неправильно?


person DaveR    schedule 22.01.2015    source источник


Ответы (3)


Вы не делаете ничего плохого, обязательно. Проблема здесь в том, что ожидания gmock проверяются в деструкторе фиктивного объекта, поэтому, если деструктор никогда не вызывается, ожидания никогда не проверяются. Это то, что происходит в вашем примере.

Простой способ обойти это — явно проверить ожидания на макете:

Mock::VerifyAndClearExpectations(foo);

Это даст вам поведение, которое вы ищете.

person Ian    schedule 22.01.2015
comment
VerifyAndClearExpectations будет работать, но я думаю, что правильное поведение здесь — просто удалить фиктивный объект в конце теста. - person VladLosev; 23.01.2015
comment
Это также возможно, хотя я предполагаю, что вариант использования здесь заключается в передаче права собственности на фиктивный объект какому-либо другому классу и проверке того, что другой класс правильно избавляется от фиктивного объекта. Удаление макета в конце теста не позволит провести такую ​​проверку. - person Ian; 23.01.2015
comment
Ян прав. В моем реальном тесте передается право собственности на макет, и я хочу убедиться, что макет действительно удален. - person DaveR; 24.01.2015
comment
Если этот компонент действительно удалит макет, вы не увидите эту ошибку. Если это не так и ожидается, что это сообщение только что обнаружило проблему в этом коде. Вам просто нужно убедиться, что деструктор Foo является виртуальным. - person VladLosev; 28.01.2015
comment
Я согласен; жаль, что этот тест проходит. Насколько я понимаю, это ограничение связано с тем, как реализуются фиктивные объекты. Учитывая текущий дизайн (т.е. ожидания проверяются при уничтожении фиктивных объектов), я не уверен, что здесь возможно «правильное» поведение. Если вы можете придумать способ решить проблему, я был бы рад услышать это :) - person Ian; 11.09.2015

Удалите объект foo в конце теста, чтобы не было утечки объекта.

person Swapnil    schedule 29.08.2015
comment
Я думаю, вы упустили суть поста. Дело в том, что тест проходит, когда не должен. Поскольку ожидание не оправдалось, тест должен завершиться неудачно. Упоминание сообщения об ошибке об утечке объекта было просто примечанием. Как заметил Ян, добавление Mock::VerifyAndClearExpectations(foo) в тест приводит к его сбою. - person DaveR; 11.09.2015

Чтобы избежать сообщения об утечке памяти, вы можете проверить возвращаемое значение Mock::VerifyAndClearExpectations(foo) и явно удалить объект, если оно ложно.

person Pavel Isaev    schedule 26.09.2017