假设我们有一个名为批准的订单类。调用此方法时,它会检查某些条件,并将Order置于Approved状态或抛出异常。在服务层,我们有类似的东西:
var order = _repository.Single(o => o.ID == orderID);
order.Approve();
_context.SaveChanges(); // or _session.SaveChanges();
有两种方法可以测试这种方法,我想听听你对此的见解:
解决方案1 :存储存储库以返回Order对象。然后断言订单处于“已批准”状态。
解决方案2 :存储存储库以返回Mock Order对象。断言调用了Approve()方法。
解决方案1更容易,我个人更青睐基于状态的测试到基于交互的测试,因为后者可以针对实现细节,应该避免。但是,我认为测试给定订单处于Approved状态并不是此服务方法的关注点。我认为我们需要一个单独的测试方法来测试Order类是否抛出异常或者Order的状态是否更改为Approved。
解决方案2可能听起来合乎逻辑,因为我们将批准订单的责任委托给订单类本身。因此,我们可能需要对此服务方法进行2次测试:一种是确保将批准订单的任务委托给Order类,另一种是确保它保存更改。
您对此有何看法?您更喜欢哪种解决方案?
干杯
答案 0 :(得分:4)
单元测试用于测试观察到的行为是否符合期望/规范。
您的问题的答案归结为您认为在这种情况下的“预期行为”: a)如果预期的行为是订单在调用服务方法后处于批准状态,那么测试状态; b)如果预期的行为是委托批准操作,则测试方法调用。
在任何一种情况下,您都需要测试Order
对象的行为(以便调用Approve()
将状态更改为已批准)。
第二个解决方案可以很好地解决两个对象的行为,但是如果有多种方式可以使订单处于批准状态(这就是你正在测试的 - 例如a)),那么你不必要地限制接受的行为。
另外,如果对于批准部分不是必不可少的话,我会创建一个单独的测试来测试保存部分