You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Espresso测试中pressBack()无效问题求助

Espresso测试中pressBack()无法返回至MainActivity的问题解决

问题描述

我是Espresso测试新手,测试里调用pressBack()本应从第二个Activity返回MainActivity,但操作无效,还触发了NoMatchingViewException,试了多种方案仍未解决,求帮助。

测试代码

import android.app.Activity
import android.app.Instrumentation
import android.content.Intent
import android.content.pm.ActivityInfo
import android.util.Log
import android.widget.TextView
import androidx.test.core.app.ActivityScenario
import androidx.test.espresso.Espresso.onView
import androidx.test.espresso.action.ViewActions
import androidx.test.espresso.action.ViewActions.*
import androidx.test.espresso.assertion.ViewAssertions.matches
import androidx.test.espresso.intent.Intents
import androidx.test.espresso.intent.matcher.IntentMatchers
import androidx.test.espresso.matcher.ViewMatchers.*
import androidx.test.ext.junit.rules.ActivityScenarioRule
import androidx.test.ext.junit.runners.AndroidJUnit4
import androidx.test.filters.LargeTest
import androidx.test.platform.app.InstrumentationRegistry
import androidx.test.uiautomator.UiDevice
import org.junit.After
import org.junit.Before
import org.junit.Rule
import org.junit.Test
import org.junit.runner.RunWith
/**
 * Instrumented test, which will execute on an Android device.
 *
 * See [testing documentation](http://d.android.com/tools/testing).
 */

@LargeTest
@RunWith(AndroidJUnit4::class)
class MainActivityTest {
    private var ivWeribeeZoo = 0
    private var tvWeribeeName = 0
    private var tvWeribeeRating = 0
    private var ieWeribeeName = 0
    private var etWeribeeRate = 0
    private var ieDate = 0

    @get:Rule
    var activityRule: ActivityScenarioRule<MainActivity>
            = ActivityScenarioRule(MainActivity::class.java)


    @Before
    fun setUP()
    {
        ivWeribeeZoo = R.id.ivWeribeeZoo
        tvWeribeeName = R.id.tvZooName
        tvWeribeeRating = R.id.suRating
        ieWeribeeName = R.id.itName
        etWeribeeRate = R.id.etRating
        ieDate = R.id.itDate

    }


    @Test
    fun nameInMainMatchesNewName() {
        //val activityScenario = ActivityScenario.launch(MainActivity::class.java)

        onView(withId(ivWeribeeZoo)).perform(click())
        onView(withId(ieWeribeeName)).perform(clearText(), typeText("ZOO"))


        closeSoftKeyboard()

        /* val mDevice:UiDevice = UiDevice.getInstance(InstrumentationRegistry.getInstrumentation())
         mDevice.pressBack()*/

        onView(isRoot()).perform(pressBack())

        onView(withId(tvWeribeeName)).check(matches(withText("ZOO")))

    }
}

可行解决方向

  • 确认软键盘彻底关闭:closeSoftKeyboard()可能未完全收起键盘,导致pressBack()先关闭键盘而非返回Activity。可添加短暂等待确保状态稳定:
    Thread.sleep(500)
    onView(isRoot()).perform(pressBack())
    
  • 改用UiDevice模拟返回键:系统级的返回键模拟不受View树限制,可靠性更高,恢复你注释的代码即可:
    val mDevice: UiDevice = UiDevice.getInstance(InstrumentationRegistry.getInstrumentation())
    mDevice.pressBack()
    
  • 验证第二个Activity启动状态:确保点击操作确实成功跳转,添加Intent验证确认页面切换:
    @Before
    fun setUp() {
        Intents.init()
        // 原有初始化代码
    }
    
    @After
    fun tearDown() {
        Intents.release()
    }
    
    @Test
    fun nameInMainMatchesNewName() {
        onView(withId(ivWeribeeZoo)).perform(click())
        // 验证目标Activity是否启动
        intended(IntentMatchers.hasComponent(SecondActivity::class.java.name))
        
        onView(withId(ieWeribeeName)).perform(clearText(), typeText("ZOO"))
        closeSoftKeyboard()
        
        onView(isRoot()).perform(pressBack())
        
        onView(withId(tvWeribeeName)).check(matches(withText("ZOO")))
    }
    
  • 检查Activity启动模式:若第二个Activity的launchMode为singleTask或singleInstance,会导致返回行为异常,需确认AndroidManifest.xml中的配置是否符合预期。
  • 确保MainActivity刷新数据:返回后MainActivity需正确更新UI,检查是否在onResume()中重新加载数据,或第二个Activity是否通过Intent、ViewModel等方式传递了更新后的名称。

内容的提问来源于stack exchange,提问作者student

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.19 07:55:29