如何在编写 espresso 测试时设置 dagger-android 2.15 后进行模拟?
How to mock after setup dagger-android 2.15 when writing espresso tests?
如果我们只使用普通匕首 2。在 application
class 中,我们将有一个 属性 持有 AppComponent
。然后我们可以在浓缩咖啡测试期间交换它。
但是当我使用 dagger-android 2.15
设置我的项目时。如果采用过多的 Dagger 魔法,事情就会变得更加含蓄。代码更干净,但让测试有点困难。
这是application
class:
class App : DaggerApplication() {
override fun applicationInjector(): AndroidInjector<out DaggerApplication> {
return DaggerAppComponent
.builder()
.create(this)
.build()
}
}
这是主页活动
class HomeActivity : DaggerAppCompatActivity() {
@Inject
lateinit var userPreference: UserPreference
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_home)
if (!this.userPreference.memberRegistered) {
goToActivity(EntryActivity::class.java)
}
}
}
以这段代码为例。如何模拟注入的 userPreference.memberRegistered
这可能是下面的 HTTP 调用?
我昨天写了一篇博客 post 解释了如何做到这一点:https://dev.to/autonomousapps/the-daggerandroid-missing-documentation-33kj
我不打算为这个答案重复整个 post(用 Dagger 正确设置测试工具需要数百个单词和代码行),但尝试总结一下:
- 在
debug
源集中添加自定义应用程序 class(我假设它也适用于 androidTest
源集,但我没有尝试过)。
- 您还需要在同一源集中的
AndroidManifest.xml
中引用此应用程序。
- 在您的 androidTest class 中创建一个 "Test component" 从您的生产顶级组件扩展并构建它。
- 使用该测试组件注入您的应用程序,这意味着您刚刚将整个 Dagger 依赖关系图替换为您专门为测试套件定义的新依赖关系图。
- 利润。
对于那些对此感兴趣的人,我得到了一个 blog 详细的步骤:
基本上,这个想法是:
- 您仍然在@Module 中生成用于注入的实例
- 但是我们将创建新的@Component A 仅用于测试
- 这个@Component 将有一个方法来获取那个@Module
- 在测试期间,我们将应用程序使用的 @Component 与我们的组件 A 交换
那就简单了:
没有 DaggerMock
- 在@Module 中,您只是 return mockito mock,而不是 return 真实实例。
使用 DaggerMock
- 您声明要交换的类型并模拟它
- 然后您可以使用模拟。
- 无需更改@Module
它受到@AutonomousApps 的解决方案的启发,但不同之处在于现在您不需要为每个测试编写@Component、@Module class。
在尝试了多种方法后,this 是唯一对我有用的方法。
如果我们只使用普通匕首 2。在 application
class 中,我们将有一个 属性 持有 AppComponent
。然后我们可以在浓缩咖啡测试期间交换它。
但是当我使用 dagger-android 2.15
设置我的项目时。如果采用过多的 Dagger 魔法,事情就会变得更加含蓄。代码更干净,但让测试有点困难。
这是application
class:
class App : DaggerApplication() {
override fun applicationInjector(): AndroidInjector<out DaggerApplication> {
return DaggerAppComponent
.builder()
.create(this)
.build()
}
}
这是主页活动
class HomeActivity : DaggerAppCompatActivity() {
@Inject
lateinit var userPreference: UserPreference
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_home)
if (!this.userPreference.memberRegistered) {
goToActivity(EntryActivity::class.java)
}
}
}
以这段代码为例。如何模拟注入的 userPreference.memberRegistered
这可能是下面的 HTTP 调用?
我昨天写了一篇博客 post 解释了如何做到这一点:https://dev.to/autonomousapps/the-daggerandroid-missing-documentation-33kj
我不打算为这个答案重复整个 post(用 Dagger 正确设置测试工具需要数百个单词和代码行),但尝试总结一下:
- 在
debug
源集中添加自定义应用程序 class(我假设它也适用于androidTest
源集,但我没有尝试过)。 - 您还需要在同一源集中的
AndroidManifest.xml
中引用此应用程序。 - 在您的 androidTest class 中创建一个 "Test component" 从您的生产顶级组件扩展并构建它。
- 使用该测试组件注入您的应用程序,这意味着您刚刚将整个 Dagger 依赖关系图替换为您专门为测试套件定义的新依赖关系图。
- 利润。
对于那些对此感兴趣的人,我得到了一个 blog 详细的步骤:
基本上,这个想法是:
- 您仍然在@Module 中生成用于注入的实例
- 但是我们将创建新的@Component A 仅用于测试
- 这个@Component 将有一个方法来获取那个@Module
- 在测试期间,我们将应用程序使用的 @Component 与我们的组件 A 交换
那就简单了:
没有 DaggerMock
- 在@Module 中,您只是 return mockito mock,而不是 return 真实实例。
使用 DaggerMock
- 您声明要交换的类型并模拟它
- 然后您可以使用模拟。
- 无需更改@Module
它受到@AutonomousApps 的解决方案的启发,但不同之处在于现在您不需要为每个测试编写@Component、@Module class。
在尝试了多种方法后,this 是唯一对我有用的方法。