[go: nahoru, domu]

blob: 2a41cf54da750fd265b35b49b362734a0901e19c [file] [log] [blame]
wolenetz@chromium.org60e281062013-02-07 19:20:211// Copyright (c) 2013 The Chromium Authors. All rights reserved.
stoyan@google.com530a94a2009-10-27 00:05:002// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#ifndef TESTING_GMOCK_MUTANT_H_
6#define TESTING_GMOCK_MUTANT_H_
7
8// The intention of this file is to make possible using GMock actions in
tzik651fa122016-02-10 18:30:189// all of its syntactic beauty.
stoyan@google.com530a94a2009-10-27 00:05:0010//
11//
12// Sample usage with gMock:
13//
14// struct Mock : public ObjectDelegate {
15// MOCK_METHOD2(string, OnRequest(int n, const string& request));
16// MOCK_METHOD1(void, OnQuit(int exit_code));
17// MOCK_METHOD2(void, LogMessage(int level, const string& message));
18//
19// string HandleFlowers(const string& reply, int n, const string& request) {
20// string result = SStringPrintf("In request of %d %s ", n, request);
21// for (int i = 0; i < n; ++i) result.append(reply)
22// return result;
23// }
24//
25// void DoLogMessage(int level, const string& message) {
26// }
27//
28// void QuitMessageLoop(int seconds) {
xhwang@chromium.org1446016c2013-05-01 16:11:0329// base::MessageLoop* loop = base::MessageLoop::current();
ki.stfu94337f42015-10-23 11:24:2030// loop->PostDelayedTask(FROM_HERE,
31// base::MessageLoop::QuitWhenIdleClosure(),
stoyan@google.com530a94a2009-10-27 00:05:0032// 1000 * seconds);
33// }
34// };
35//
36// Mock mock;
37// // Will invoke mock.HandleFlowers("orchids", n, request)
38// // "orchids" is a pre-bound argument, and <n> and <request> are call-time
39// // arguments - they are not known until the OnRequest mock is invoked.
brettw44ce0ec52015-06-12 01:57:5740// EXPECT_CALL(mock, OnRequest(Ge(5), base::StartsWith("flower"))
stoyan@google.com530a94a2009-10-27 00:05:0041// .Times(1)
tzik651fa122016-02-10 18:30:1842// .WillOnce(Invoke(CreateFunctor(
43// &Mock::HandleFlowers, base::Unretained(&mock), string("orchids"))));
stoyan@google.com530a94a2009-10-27 00:05:0044//
45//
46// // No pre-bound arguments, two call-time arguments passed
47// // directly to DoLogMessage
48// EXPECT_CALL(mock, OnLogMessage(_, _))
49// .Times(AnyNumber())
tzik651fa122016-02-10 18:30:1850// .WillAlways(Invoke(CreateFunctor(
51// &Mock::DoLogMessage, base::Unretained(&mock))));
stoyan@google.com530a94a2009-10-27 00:05:0052//
53//
54// // In this case we have a single pre-bound argument - 3. We ignore
55// // all of the arguments of OnQuit.
56// EXCEPT_CALL(mock, OnQuit(_))
57// .Times(1)
58// .WillOnce(InvokeWithoutArgs(CreateFunctor(
tzik651fa122016-02-10 18:30:1859// &Mock::QuitMessageLoop, base::Unretained(&mock), 3)));
stoyan@google.com530a94a2009-10-27 00:05:0060//
61// MessageLoop loop;
62// loop.Run();
63//
64//
65// // Here is another example of how we can set an action that invokes
66// // method of an object that is not yet created.
67// struct Mock : public ObjectDelegate {
68// MOCK_METHOD1(void, DemiurgeCreated(Demiurge*));
69// MOCK_METHOD2(void, OnRequest(int count, const string&));
70//
71// void StoreDemiurge(Demiurge* w) {
72// demiurge_ = w;
73// }
74//
75// Demiurge* demiurge;
76// }
77//
78// EXPECT_CALL(mock, DemiurgeCreated(_)).Times(1)
tzik651fa122016-02-10 18:30:1879// .WillOnce(Invoke(CreateFunctor(
80// &Mock::StoreDemiurge, base::Unretained(&mock))));
stoyan@google.com530a94a2009-10-27 00:05:0081//
82// EXPECT_CALL(mock, OnRequest(_, StrEq("Moby Dick")))
83// .Times(AnyNumber())
tzik651fa122016-02-10 18:30:1884// .WillAlways(WithArgs<0>(Invoke(CreateFunctor(
85// &Demiurge::DecreaseMonsters, base::Unretained(&mock->demiurge_)))));
stoyan@google.com530a94a2009-10-27 00:05:0086//
87
tzik651fa122016-02-10 18:30:1888#include "base/bind.h"
stoyan@google.com530a94a2009-10-27 00:05:0089
90namespace testing {
91
tzik651fa122016-02-10 18:30:1892template <typename Signature>
93class CallbackToFunctorHelper;
stoyan@google.com530a94a2009-10-27 00:05:0094
tzik651fa122016-02-10 18:30:1895template <typename R, typename... Args>
96class CallbackToFunctorHelper<R(Args...)> {
stoyan@google.com530a94a2009-10-27 00:05:0097 public:
tzik651fa122016-02-10 18:30:1898 explicit CallbackToFunctorHelper(const base::Callback<R(Args...)>& cb)
99 : cb_(cb) {}
stoyan@google.com530a94a2009-10-27 00:05:00100
tzik651fa122016-02-10 18:30:18101 template <typename... RunArgs>
102 R operator()(RunArgs&&... args) {
103 return cb_.Run(std::forward<RunArgs>(args)...);
stoyan@google.com530a94a2009-10-27 00:05:00104 }
105
106 private:
tzik651fa122016-02-10 18:30:18107 base::Callback<R(Args...)> cb_;
stoyan@google.com530a94a2009-10-27 00:05:00108};
109
tzik651fa122016-02-10 18:30:18110template <typename Signature>
111CallbackToFunctorHelper<Signature>
112CallbackToFunctor(const base::Callback<Signature>& cb) {
113 return CallbackToFunctorHelper<Signature>(cb);
stoyan@google.com530a94a2009-10-27 00:05:00114}
115
tzik2e53fef92017-03-20 07:14:07116template <typename Functor>
117CallbackToFunctorHelper<typename Functor::RunType> CreateFunctor(
118 Functor functor) {
119 return CallbackToFunctor(functor);
120}
121
tzik651fa122016-02-10 18:30:18122template <typename Functor, typename... BoundArgs>
123CallbackToFunctorHelper<base::MakeUnboundRunType<Functor, BoundArgs...>>
124CreateFunctor(Functor functor, const BoundArgs&... args) {
125 return CallbackToFunctor(base::Bind(functor, args...));
amit@chromium.org4e676aa2010-02-12 18:19:07126}
amit@chromium.org4e676aa2010-02-12 18:19:07127
stoyan@google.com530a94a2009-10-27 00:05:00128} // namespace testing
129
130#endif // TESTING_GMOCK_MUTANT_H_