ary*_*axt 9 unit-testing objective-c ios
我遇到过很多情况,我的核心逻辑是私有方法.您将如何进行单元测试,是否有任何类型的编译时操作来忽略未知/私有方法的编译错误?我知道对于代码的第二部分我可以使用performSelector,但这是一个合理的解决方案吗?
例如:
[[self.objectMock expect] privateMethod];
or
[self.object callPrivateMethodsToExpectSomeOtherBehaviour]
Run Code Online (Sandbox Code Playgroud)
编辑:
这是一个示例,用于说明为什么我需要测试一些私有方法.这些测试不合理吗?我怎么测试调用clear实际上做了它想做的事情?
- (void)clear
{
self.orderNumber = nil;
[self.items removeAllObjects];
// Clear the rest of fields
}
- (void)testClearShouldRemoveOrderNumber
{
Order *order = [[Order alloc] init];
OCMockObject *orderPartialMock = [OCmockObject partialMockForObject:order];
[[orderPartialMock.items expect] setOrderNumber:nil];
[orderPartialMock clear];
[orderPartialMock verify];
}
- (void)testClearShouldRemoveItems
{
Order *order = [[Order alloc] init];
order.items = [[OCMockObject niceMockForClass:[NSMutableArray class]];
[[orderPartialMock.items expect] removeAllObjects];
[orderPartialMock performSelector@selector(clear)];
[orderPartialMock.items verify];
}
Run Code Online (Sandbox Code Playgroud)
Jod*_*ins 13
方法永远不会是"私有"的,因为一旦一个类实现了一个方法,它就可以发送给我的任何人.
所以,假设你有一个Foo带有"私有"方法的类bar,它不在接口声明中.您可以从任何地方仍然调用,bar但您可能会获得编译器诊断.
可能最简单的方法是在测试使用的类别中声明方法.例如:
@interface Foo (MyPrivateMethodsUsedForTesting)
- (void)bar;
@end
Run Code Online (Sandbox Code Playgroud)
现在,您可以在没有编译器抱怨的情况下使用它们.注意,这些方法不必在实际MyPrivateMethodsUsedForTesting类别中实现.这种技术有时也被称为"非正式协议".
编辑
另外,正如其他人所指出的那样,如果您需要访问私有方法,您可能应该重新访问您的设计.大约30年后这样做,肯定有时候,特别是测试,你需要访问私人的东西,但大多数情况下,它意味着某种类型的设计审查是有序的.
您不应该直接测试您的私有方法.相反,您需要通过公共方法测试它们.这是关于programmers.stackexchange.com讨论此事的问题的链接.
答案的一般概念是,您(或维护您的代码的任何其他人)可以随时通过更改签名,更改实现或完全删除它们来更改您的私有方法.你班上没有人应该关心 - 毕竟,这是首先让这些方法变得私密的主要驱动力.
如果以不兼容的方式更改私有方法,则必须中断公共方法的单元测试; 否则,你没有做好测试你的公共方法的工作.实际上,这使得私有方法的单元测试变得不必要.
通常,您不需要对私有方法进行单元测试.
公开的方法告诉你你的课程做了什么 - 这是你关心的,你应该测试这些.私有方法关注你的类如何完成它的工作,你的测试不应该关心如何完成工作,只要它正确完成.
如果有一天你决定改变你的类的工作方式(即通过改变私有方法中的代码),而不改变你的类实际做的事情,那么你的单元测试应该继续通过.通过尝试测试你的类的内部,你创建了一个脆弱的测试,即使该类仍然正常工作可能会破坏.
如果您发现很难通过公共方法彻底测试您的课程,那么这是一个警示标志,您的课程可能太大 - 考虑将其分解成更小的部分.
| 归档时间: |
|
| 查看次数: |
5824 次 |
| 最近记录: |