PhoneNumberSelectionActivity转Kotlin后Mockk verify报Missing calls错误
问题根因
- Kotlin转换过程中给
@IntDef注解额外添加了flag = true配置,原Java代码未开启flag模式,导致Mockk对带注解的Int参数识别异常,匹配签名失败。 - 修改后的测试代码错误将
PhoneNumberSelectionActivity.startActivity的返回值设置为mockk(),Mockk直接拦截跳过了方法内部的执行逻辑,Intent未被初始化,才出现startActivity(null)的报错。 - 额外添加的
mockkConstructor和实例方法verify属于冗余配置,和你要验证的静态方法调用逻辑无关,反而会增加Mock匹配冲突概率。 - 你使用的Mockk 1.9.3版本较老旧,对Kotlin 1.4+版本的带注解静态方法参数匹配存在兼容性bug。
修复方案
步骤1:修复IntDef注解
删除@IntDef中多余的flag = true配置,和原Java逻辑对齐:
@IntDef( value = [FRAGMENT_TRANSITION.AREA_CODE_TO_PHONE_SELECTION, FRAGMENT_TRANSITION.PHONE_SELECTION_TO_AREA_CODE] ) @kotlin.annotation.Retention(AnnotationRetention.SOURCE) annotation class FRAGMENT_TRANSITION { companion object { const val AREA_CODE_TO_PHONE_SELECTION = 0 const val PHONE_SELECTION_TO_AREA_CODE = 1 } } @IntDef( value = [ACTIVITY_HOST_TYPE.OTHER, ACTIVITY_HOST_TYPE.AUTHORIZATION, ACTIVITY_HOST_TYPE.PERSONALIZED_ONBOARDING] ) @kotlin.annotation.Retention(AnnotationRetention.SOURCE) annotation class ACTIVITY_HOST_TYPE { companion object { const val OTHER = -1 const val AUTHORIZATION = 0 const val PERSONALIZED_ONBOARDING = 1 } }
步骤2:修正测试代码
删除冗余配置,修正静态方法返回值,使用eq()匹配器显式包装参数避免注解导致的匹配问题:
@Test fun `handle signed in but no phone number goes to PNS`() { mockSessionInfo(sessionId = "session", userName = "name", phone = null) mockkStatic(PhoneNumberSelectionActivity::class) // 静态方法返回类型为Unit,对齐实际逻辑 every { PhoneNumberSelectionActivity.startActivity( eq(mockActivity), any(), any() ) } answers { callOriginal() } // 可选,如果你需要执行方法内部逻辑就加,不需要就直接returns Unit every { mockActivity.dismissProgressDialog() } just Runs every { mockActivity.startActivity(any<Intent>()) } returns Unit assertFalse(authorizationUtils.handleNotSignedInNoPhoneNumber(mockActivity)) verify { PhoneNumberSelectionActivity.startActivity( eq(mockActivity), eq(true), eq(PhoneNumberSelectionActivity.ACTIVITY_HOST_TYPE.AUTHORIZATION) ) } }
步骤3(可选,兼容性优化)
将Mockk版本升级到1.12.0及以上,修复老旧版本的参数匹配兼容性问题。
内容的提问来源于stack exchange,提问作者Kristy Welsh
相关产品推荐
相关产品推荐

