0

I'm a beginner with google mock and I'm not sure how to use it and the concept.

If I'm trying to Test a method from a class that is calling some other methods from different classes. Do I need to mock all these methods from this different classes that my Test method is calling. Here is a example:

 class A { public: A () {} int setnum(int num) {//do some stuff return 1 or 0// } private: int _num; }; class B { public: B (){} int init(A *a, int number){ if(a->setnum(number)) return 1; return 0; } void setNum(int num){_num=num;} private: A *_a; int _num; }; class C { public: int doSoemthing(A *a, int number){ if (domore(a,number)) return 1; return 0; } int domore(A *a, int number){ if(_b.init(a,number)) return 1; return 0; ;} private: B _b; }; 

Do I need to mock all the methods from class A and B that I need to Test my Test method? Or can I just mock one Class , and test if this class is working.

2 Answers 2

3

In order to test C class with mocks, you need to introduce an interface for the dependency than is to be used in C class (here, added BIface). Then you need to use dependency injection of BIface to C class (via added ctor). Having that you will be able to test interactions of B and C classes. IMO A class doesn't need to be mocked in CTest (but most probably need to be tested in BTest)

class A { public: A() {} // not needed int setnum(int num) { // do some stuff return 1 or 0// } private: int _num; }; class BIface { public: virtual ~BIface() = default; virtual int init(A *a, int number) = 0; virtual void setNum(int num) = 0; }; class B : public BIface { public: B() {} // not needed int init(A *a, int number) override { if (a->setnum(number)) return 1; return 0; } void setNum(int num) override { _num = num; } private: A *_a; int _num; }; class C { public: C(BIface &b) : _b{b} {} int doSoemthing(A *a, int number) { if (domore(a, number)) return 1; return 0; } int domore(A *a, int number) { if (_b.init(a, number)) return 1; return 0; ; } private: BIface &_b; }; class BIfaceMock : public BIface { public: MOCK_METHOD2(init, int(A *, int)); MOCK_METHOD1(setNum, void(int)); }; TEST(CTest, givenDoingMoreWhenInitOfBReturnOneThenReturnOne) { // can be done in CTest ctor if more tests are needed to avoid code duplciation BIfaceMock bMock{}; A a{}; // `a` doesn't need to be mocked in CTest. It shall be mocked in BTest as it is dependency of B class, not C class C testedObject{bMock}; // dependency injection of BFace to C const auto SOME_INT_PARAM = 42; // Eq mather is used to match both &a and SOME_INT_PARAM. This confirms proper parameters were passed to init EXPECT_CALL(bMock, init(&a, SOME_INT_PARAM)).WillOnce(Return(1)); ASSERT_EQ(1, testedObject.domore(&a, SOME_INT_PARAM)); } 
Sign up to request clarification or add additional context in comments.

1 Comment

yes that is exactly how i started, but I was not sure if I need to mock class A,This is just a part of the code, it is a little bit complex I have singleton classes and I need to refactor the code to be able to test. But that's the answer I was searching for. Many Thanks
0

I'm not 100% sure but in your example you don't have to use mocks at all. You can create your objects really easy here.

I would use mocks when I would expect that some method will be called and should return specific value - I'm not testing this method but for example if-statment:

 A a; if(a.method()) { // some logic } 
  • To manipulate what if will get I would use mocks like this: EXPECT_CALL(aMock.method()).WillOnce(Return(true)); But you can use it in many more situations (e.g: you can avoid creating really big class and replace it with mock object).

4 Comments

Sorry my mistake, I edit the code. This is just a simple example I have a much complicated code. So my question is do I need to mock A and B in this example
Even after code change you don't have to use mocks here. I see one situation if: int doMore(){ D d; if(d.isValid()){return 1;} return 0; } looks something like this (isValud() - return some value) -> if you want to in easy way control test-flow you can use mocks to accomplish it. Using mocks you can have two simple tests and test if your method return 1 and 0 with proper condition.
But what if doMore() depends from a method in class A
You can do it on this case but IMO with this kind od trivial classes you can create real objects(instead od nocka) in test case

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.