Robolectric和测试startActivityForResult

3

我的 Robolectric 单元测试遇到了问题。

我可以轻松地断言,当监听器使用方法 startActivity( Intent ) 时,一个单击会启动新活动。

但似乎当使用方法 startActivityForResult(Intent, int) 启动新活动时,Robolectric 遇到了问题:在代码中添加一些断点后,我发现活动并没有启动(只需将其更改为使用方法 startActivity( Intent ) 就能使断言通过)。

这是正常的吗?这很遗憾,因为我的应用程序的第一个活动使用 startActivityForResult(Intent, int) 方法。

是否有人成功地使用这种启动活动的方式进行测试?

感谢您的帮助..

2个回答

5
你的问题的简短回答是,由于Robolectric将Android类转换为在JVM中执行的代码的方式,许多功能不像您期望的那样运行。许多系统回调不会执行,您必须依赖Robolectric提供的类的Shadow实现。 (请参见@Steven_BDawg提供的链接)。
长答案:也许可以在一个大测试中实现整个流程,但这不是框架设计的方式。
Robolectric和单元测试一般不应该按照您描述的方式使用。 维基百科上的单元测试页面 指出,一个单位可以被视为应用程序中最小的可测试部分。 单元测试套件应包含许多轻量级测试,其中每个测试都隔离了应用程序中的一部分功能并确保其正常工作。
考虑一个基本应用程序,其中包含两个Activity,A和B。 Activity A显示有关主题的一些信息,而Activity B允许用户选择要在A中显示的主题。 当用户从Activity A移动到Activity B时,B将使用startActivityForResult()调用,并应返回所选主题到A。

现在假设我们想要对A从B获取结果并显示数据的流程进行单元测试。我们可以将其分为两个测试:

  1. 被测试的活动 - 活动A。在我们的测试中,我们将创建Activity A的一个新实例。在Robolectric测试中,我们创建了我们期望B返回给A的Intent,并调用A的影子方法receiveResult(),使用OK结果代码和这个Intent填充参数。在receiveResult()之后,运行你的断言。现在你知道Activity A正确地处理了结果!
  2. 被测试的活动 - 活动B。在我们的测试中,我们将创建Activity B的一个新实例,并将其设置为从Activity A开始进行结果设置。在Robolectric测试中,我们将执行所有需要选择数据的操作,创建我们将发送回去的意图,然后对该意图进行断言,以确保它被正确创建。

这是一个非常简单的例子。这两个步骤可能可以分解为更多的测试,因为每个单元测试应该只测试你的应用程序可以分解成的最小功能单元。这个例子主要是帮助您开始以单元测试的方式思考。我发现随着我对单元测试的理解加深,编写代码的方式也发生了变化。我尽量避免以一种过于复杂而无法进行适当单元测试的方式编写方法和类。作为经验法则,易于进行单元测试的代码执行非常具体的操作,在第一次阅读代码时就能够清楚地看到。

最后,如果您想进一步进行,模拟框架可以极大地帮助您进行单元测试。 Mockito是我过去成功使用的一个模拟框架。模拟框架的目的是创建存根对象,其行为由您严密控制。 Mockito(或任何其他模拟框架)将允许您定义一个从您需要的任何类型扩展的对象,并仅实现您需要的方法。您将能够直接控制对任何这些方法调用的响应。这有助于单元测试,因为您只需要真正的测试对象;通过模拟所有其他对象,您将更好地了解测试对象是否正常运行,因为所有其他行为都由您明确定义,作为测试人员。 (是的,这确实会导致大量额外的代码,但这就是一个好的单元测试人员的生活。然而,正如先前所述,随着您对单元测试的熟悉程度越来越高,您可能会发现自己编写的方法需要更少的模拟,并且更有利于编写测试。有些程序员甚至会在编码之前编写他们的单元测试,以保持他们的代码紧凑,并专注于单一目的)

希望这可以帮到您!


当然有帮助,谢谢!现在一切都变得更加清晰了,特别是你给出的这个简单而有效的例子。我也考虑使用模拟对象,所以我也会研究单元测试的这个方面。非常感谢! - user1987343

3

1
谢谢,我已经阅读了这个页面,但不幸的是我认为它对我的问题没有太大帮助。那个人正在模拟一个活动的行为,该活动会将结果发送给另一个监听结果的活动。我指出Robolectric似乎无法在使用startActivityForResult方法时有效地启动一个活动...尽管如此,还是感谢您的帮助 :) - user1987343

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接