如何阻塞等待GMock对象的预期调用达成?
主线程阻塞等待GMock预期调用完成的实现方案
当然可以实现,这里提供两种实用的解决方式:
方法一:使用GMock内置的等待函数(推荐)
GMock 1.10及以上版本提供了testing::Mock::WaitForAllExpectations()接口,它会阻塞当前线程,直到所有已声明的预期调用都被满足,或者到达超时时间(默认10秒,也可自定义超时时长)。
修改后的代码示例:
EXPECT_CALL(mockObj, fn()).Times(1); // 声明预期调用 operation(); // 触发其他线程调用fn() // 阻塞等待所有预期完成,断言确保等待成功 ASSERT_TRUE(testing::Mock::WaitForAllExpectations()); // 也可以指定超时,比如5秒: // ASSERT_TRUE(testing::Mock::WaitForAllExpectations(std::chrono::seconds(5))); operation_after_fn_called(); // 预期完成后执行后续操作
方法二:自定义条件变量配合GMock动作
如果你的GMock版本较低,不支持内置等待函数,可以手动通过条件变量实现线程同步:
#include <condition_variable> #include <mutex> std::mutex g_mtx; std::condition_variable g_cv; bool g_fn_called = false; TEST(YourTestSuite, YourTestCase) { EXPECT_CALL(mockObj, fn()) .Times(1) .WillOnce(testing::Invoke([]() { // 调用fn时标记状态并通知主线程 std::lock_guard<std::mutex> lock(g_mtx); g_fn_called = true; g_cv.notify_one(); })); operation(); // 触发其他线程执行fn() // 主线程阻塞等待,直到fn被调用 std::unique_lock<std::mutex> lock(g_mtx); g_cv.wait(lock, []{ return g_fn_called; }); operation_after_fn_called(); // 执行后续操作 }
关键注意点
- 使用内置等待函数时,要确保所有预期是必须被满足的(比如
Times(1)),如果是Times(AtMost(1))这类非强制预期,函数会一直等待到超时。 - 自定义同步逻辑时,必须保证线程安全,避免出现竞态条件。
内容的提问来源于stack exchange,提问作者hczstev
相关产品推荐
相关产品推荐

