https://github.com/allending/Kiwi/wiki
- 全てオブジェクトである必要がある。
- intなどはtheValue()でラップする必要がある。
- should receiveはテストするメソッド実行前に書いておく必要がある。
- should equalなどの実行結果の確認はテストするメソッド実行後に書いておく必要がある。
- stubはMockオブジェクトを使わなくても、既存のオブジェクトにも追加できる。
- stubで何か動作させたい場合は、ランタイムのメソッド入れ替えを使うしかない? (本当はテストコードだけで何とかしたい)
- expectFutureValueはオブジェクトを引数にとる
- 対象オブジェクトがnilの場合、shouldは通らない。
- stubでandReturnを使う場合は、withArgumentsで指定した引数の場合のみstubが有効になる。 引数を問わずstubを有効にする場合はwithArguments:any()とする。
- Mock、stub作成
- should receive関係設定
- テストしたいメソッド実行
- should equal関係設定
#include "Kiwi.h"
SPEC_BEGIN(TestClassSpec)
describe(@"TestClass", ^{
context(@"when xxx", ^{
it(@"should xxx", ^{
});
});
});
SPEC_END
KWMock *test = [KWMock nullMockForClass:[TestClass class]];
[test stub:@selector(count) andReturn:theValue(1)];
[[theValue(count) should] equal:theValue(10)]; // すぐ評価
[[expectFutureValue(theValue(count)) shouldEventuallyBeforeTimingOutAfter(2.0)] equal:theValue(10)]; // 2.0秒後に評価
[[string should] equal:@"test"]; // すぐ評価
[[expectFutureValue(string) shouldEventuallyBeforeTimingOutAfter(2.0)] equal:@"test"]; // 2.0秒後に評価
[object shouldBeNil];
[[[test should] receive] method:@"test"];
引数は何でも良い場合はany()を使う
[[[test should] receive] method:any()];
時間差で評価する場合
[[[test shouldEventuallyBeforeTimingOutAfter(1.0)] receive] method:@"test"];
[[[TestClass should] receive] method:@"test"];
TestClass *test = [[[TestClass alloc] init] autorelease];
[[test stub] method: any() param:NULL];
[TestClass stub:@selector(method: param:)];
ダミーでsendAsynchronousRequestを作っておき、ランタイムで差し替える こうすると実際に通信しなくてもハンドラを実行できる
TestSpec内
#import <objc/runtime.h>
:
Method original = class_getClassMethod([NSURLConnection class], @selector(sendAsynchronousRequest:queue:completionHandler:));
Method sub = class_getClassMethod([DummyClass class], @selector(sendAsynchronousRequest:queue:completionHandler:));
method_exchangeImplementations(original, sub);
// test code
method_exchangeImplementations(sub, original);
DummyClass内
// for unit test
+ (void)sendAsynchronousRequest:(NSURLRequest *)request queue:(NSOperationQueue *)queue completionHandler:(void (^)(NSURLResponse*, NSData*, NSError*))handler
{
NSHTTPURLResponse *httpResponse = [[[NSHTTPURLResponse alloc] initWithURL:nil statusCode:200 HTTPVersion:nil headerFields:nil] autorelease];
handler(httpResponse, nil, nil);
}
void (^setParameter)(int patternId);
setParameter = ^(int patternId){
// 設定
};
context(@"when xxx", ^{
it(@"should xxx", ^{
setParameter(0);
});
});