April Polubiec
April Polubiec

Reputation: 618

How to use mocks with a test fixture in GMock?

I have a test fixture in my tests so I don't have to instantiate objects of my class repeatedly, but I'm not sure how to use mocks with it. To put it simply, this is how the class is defined:

class Class1 {
public:
  Class1(std::shared_ptr<Class2> class_two);
  void doThisThing() { doThatThing(); }
}

class Class2 {
public:
  Class2(Class3* class3_ptr);
  int doThatThing();
}

(class 1 is constructed using a shared pointer to class 2. Class 2 is constructed with a pointer to class 3. Class 1 calls on a function "doThisThing" which calls Class 2's function doThatThing.)

I need to create a mock for doThatThing() (and the rest of Class2's functions), but can't figure out how to pass the mock object to Class 1. Here is what I have so far in my testing code:

class TestClass1 : public ::testing::Test {
  TestClass1(){
//Construct instance of Class1 and store as member variable
    std::shared_ptr<Class3> class_three = std::make_shared<Class3>();
    std::shared_ptr<Class2> class_two = std::make_shared<Class2>((Class3*)class_three.get());
    class_one = new Class1(class_two);
  };
Class1* class_one;
}

MockClass2 : public Class2 {
  MOCK_METHOD0(doThatThing, int());
}

TEST_F(TestClass1, doThatThingTest){
  MockClass2 mockObj;

**THIS IS WHERE I'M STUCK. How do I get that mockObj into my TestClass1 Fixture? As of now, it is calling the actual function, not the mock***

  class_one->doThatThing();
  EXPECT_CALL(mockObj, doThatThing());
}

I had to abstract and simplify the actual code, so I hope the above makes sense.

Upvotes: 2

Views: 3930

Answers (1)

Tobias Wollgam
Tobias Wollgam

Reputation: 789

Assuming that your MockClass2 works, you should try something like the following:

Here you should override the functions SetUp that is called right before every call of a test function to prepare your test data. And override TearDown that is called after every call of a test function to clean up test data.

struct TestClass1 : public ::testing::Test
{
    void SetUp() override
    {
        class_two_mock = std::make_shared<MockClass2>();
        class_one = std::make_unique<Class1>(class_two_mock);        
    }
    void TearDown() override
    {
        class_one.reset();
        class_two_mock.reset();
    }

    std::shared_ptr<MockClass2> class_two_mock
    std::unique_ptr<Class1> class_one;
};

In the test function you must declare your expectations before something is executed.

TEST_F(TestClass1, doThatThingTest)
{
    EXPECT_CALL(*class_two_mock, doThatThing());

    class_one->doThatThing();
}

You may need an interface for Class2. The code here is not tested.

Upvotes: 2

Related Questions