先日書いた GoogleTest の兄弟分である GoogleMock を Visual Studio で使ってみた。名前の通りのモックライブラリ。
ビルドでも意外と躓いたのでメモ。
#前提として GoogleTest の設定ができてることとする
はじめて使ったけど、結構いいかも
環境
- Windows 7
- Visual Studio 2008
ビルド
- http://code.google.com/p/googlemock/downloads/list からダウンロード
- 試したのは gmock-1.5.0.zip
- 解凍して読み込み専用を外し、msvc/gmock.sln を実行
- 変換ウィザードが動くので、「完了」を押す
- gmock プロジェクトの gmock-all.cc が無いとか言ってくるので、一度クリアして gmock/src にあるやつを追加
- gmock-all.cc の中でインクルードできないとか言ってくるので、#include
を #include に変える - gtest の関数の実体が無いとか言ってくるので、gmock の下にある gtest を消す
- ビルドはできるので、gmock_test を走らせる。なんか、2件の Fail が出た
- パスの設定
- Visual Studio のメニュー[ツール|オプション]を選択
- 「プロジェクトおよびソリューション|VC++ディレクトリ」(一番上に隠れてる)を選択
- 「ディレクトリを表示するプロジェクト」から「インクルードファイル」を選択し、Google Mock のインクルードパス(ここでは「<配置フォルダ>\gmock-1.5.0\include」)を追加
- 同じく「ライブラリファイル」を選択し、Google Mock のライブラリパス(ここでは「<配置フォルダ>\gmock-1.5.0\msvc\Debug」)を追加
使う
サンプル的なものを書いてみた。理解しているわけではないので、間違いがあるかもしれません。
大きく、EXPECT_CALL と ON_CALL があるようだけど、今回は EXCEPT_CALL だけー
#include <gtest/gtest.h> #include <gmock/gmock.h> #include <string> // この行を gmock/gmock.h に入れとけばライブラリリンクもいらないかな #pragma comment( lib, "gmock.lib" ) using testing::Invoke; using testing::Return; using testing::_; // インタフェース class Hello { public: virtual std::string say() = 0; }; // インタフェースのモック class MockHello : public Hello { public: MOCK_METHOD0( say, std::string () ); }; // テストしたいクラス class Greeting { Hello* hello_; public: Greeting( Hello* hello ) : hello_( hello ) {} // あいさつ std::string hello() { return hello_->say(); } // 3回挨拶 std::string hello3Times() { return hello_->say() + hello_->say() + hello_->say(); } }; // 英語であいさつ TEST( HelloTest, English ) { // モックを作って、返したいものを入れる MockHello mock_hello; EXPECT_CALL( mock_hello, say()).WillOnce( Return( "hello" ) ); // テストする Greeting greeting( &mock_hello ); EXPECT_EQ( greeting.hello(), "hello" ); } // 英語であいさつ(日本語で挨拶してしまった) TEST( HelloTest, English_Error ) { // モックを作って、返したいものを入れる MockHello mock_hello; EXPECT_CALL( mock_hello, say()).WillOnce( Return( "こんにちは" ) ); // テストする Greeting greeting( &mock_hello ); EXPECT_EQ( greeting.hello(), "hello" ); } // 日本語であいさつ TEST( HelloTest, Japanese ) { // モックを作って、返したいものを入れる MockHello mock_hello; EXPECT_CALL( mock_hello, say()).WillOnce( Return( "こんにちは" ) ); // テストする Greeting greeting( &mock_hello ); EXPECT_EQ( greeting.hello(), "こんにちは" ); } // 3回呼ぶ TEST( HelloTest, _3Times_Success ) { // モックを作って、返したいものを入れる MockHello mock_hello; EXPECT_CALL( mock_hello, say()) .Times( 3 ) .WillRepeatedly( Return( "こんにちは" ) ); // テストする Greeting greeting( &mock_hello ); EXPECT_EQ( greeting.hello3Times(), "こんにちはこんにちはこんにちは" ); } // 3回呼ぶ(と見せかけて一回しか呼ばない) TEST( HelloTest, _3Times_Error ) { // モックを作って、返したいものを入れる MockHello mock_hello; EXPECT_CALL( mock_hello, say()) .Times( 3 ) .WillRepeatedly( Return( "こんにちは" ) ); // テストする Greeting greeting( &mock_hello ); EXPECT_EQ( greeting.hello(), "こんにちは" ); } // 3回呼ぶ(3回呼ぶけど結果がダメ) TEST( HelloTest, _3Times_Error2 ) { // モックを作って、返したいものを入れる MockHello mock_hello; EXPECT_CALL( mock_hello, say()) .Times( 3 ) .WillRepeatedly( Return( "こんにちは" ) ); // テストする Greeting greeting( &mock_hello ); EXPECT_EQ( greeting.hello3Times(), "hellohellohello" ); }