ทดสอบกิจกรรมของแอป

กิจกรรมเป็นคอนเทนเนอร์สําหรับการโต้ตอบของผู้ใช้ทุกครั้งภายในแอป ดังนั้น คุณจึงควรทดสอบลักษณะการทํางานของกิจกรรมในแอปในระหว่างเหตุการณ์ระดับอุปกรณ์ เช่น เหตุการณ์ต่อไปนี้

  • แอปอื่น เช่น แอปโทรศัพท์ของอุปกรณ์ ขัดจังหวะกิจกรรมของแอป
  • ระบบจะทำลายและสร้างกิจกรรมของคุณขึ้นใหม่
  • ผู้ใช้จะวางกิจกรรมของคุณในสภาพแวดล้อมการแสดงหน้าต่างใหม่ เช่น การแสดงภาพซ้อนภาพ (PIP) หรือหลายหน้าต่าง

โดยเฉพาะอย่างยิ่ง คุณต้องตรวจสอบว่ากิจกรรมทํางานอย่างถูกต้องเพื่อตอบสนองต่อเหตุการณ์ที่อธิบายไว้ในวงจรกิจกรรม

คู่มือนี้อธิบายวิธีประเมินความสามารถของแอปในการรักษาความสมบูรณ์ของข้อมูล และประสบการณ์ของผู้ใช้ที่ดีเมื่อกิจกรรมของแอปเปลี่ยนสถานะต่างๆ ในวงจรของแอป

การทดสอบกิจกรรมใน Compose

เมื่อทดสอบแอปที่สร้างด้วย Jetpack Compose โดยปกติแล้วคุณจะใช้ createAndroidComposeRule เพื่อเปิดใช้งานกิจกรรมและโต้ตอบกับคอมโพเนนต์ UI

อย่างไรก็ตาม การทดสอบเหตุการณ์ระดับอุปกรณ์ เช่น การเปลี่ยนแปลงการกำหนดค่าหรือ กิจกรรมที่ระบบนำไปไว้เบื้องหลังหรือทำลาย จะกำหนดให้คุณ จัดการวงจรของกิจกรรมโดยตรง โดยใช้เฟรมเวิร์กActivityScenarioพื้นฐาน

กฎการทดสอบการเขียนจะตัดข้อความและจัดการสถานการณ์นี้ให้คุณโดยอัตโนมัติ ตลอดทั้งคู่มือนี้ คุณจะเห็นรูปแบบต่อไปนี้ที่ใช้เพื่อเชื่อมช่องว่าง ระหว่างการทดสอบ UI สมัยใหม่และการจัดการวงจรมาตรฐาน

@get:Rule
val composeTestRule = createAndroidComposeRule<MyActivity>()

@Test fun testEvent() {
    val scenario = composeTestRule.activityRule.scenario

    // ...
}

ขับเคลื่อนสถานะของกิจกรรม

แง่มุมที่สำคัญอย่างหนึ่งของการทดสอบกิจกรรมของแอปคือการวางกิจกรรมของแอปในสถานะที่เฉพาะเจาะจง หากต้องการกำหนดส่วน "given" ของการทดสอบ ให้ใช้อินสแตนซ์ของ ActivityScenario ซึ่งเป็นส่วนหนึ่งของไลบรารี AndroidX Test เมื่อใช้คลาสนี้ คุณจะวางกิจกรรมในสถานะที่จำลอง เหตุการณ์ระดับอุปกรณ์ได้

ActivityScenario เป็น API ข้ามแพลตฟอร์มที่คุณใช้ในการทดสอบหน่วยภายใน และการทดสอบการผสานรวมในอุปกรณ์ได้ ในอุปกรณ์จริงหรืออุปกรณ์เสมือนจริง ActivityScenario จะให้ความปลอดภัยของเธรด โดยจะซิงค์เหตุการณ์ระหว่างเธรดการวัดคุมของเทสต์กับเธรดที่เรียกใช้กิจกรรมภายใต้การทดสอบ

API นี้เหมาะอย่างยิ่งสำหรับการประเมินลักษณะการทำงานของกิจกรรมที่อยู่ระหว่างการทดสอบ เมื่อมีการทำลายหรือสร้างกิจกรรม ส่วนนี้จะแสดงกรณีการใช้งานที่พบบ่อยที่สุด ซึ่งเชื่อมโยงกับ API นี้

สร้างกิจกรรม

หากต้องการสร้างกิจกรรมภายใต้การทดสอบ ให้เพิ่มโค้ดที่แสดงในข้อมูลโค้ดต่อไปนี้

@RunWith(AndroidJUnit4::class)
class MyTestSuite {
    @Test fun testEvent() {
       launchActivity<MyActivity>().use {
       }
    }
}

หลังจากสร้างกิจกรรมแล้ว ActivityScenario จะเปลี่ยนสถานะกิจกรรมเป็น RESUMED สถานะนี้บ่งบอกว่ากิจกรรมของคุณกำลังทำงานและ ผู้ใช้มองเห็นได้ ในสถานะนี้ คุณสามารถโต้ตอบกับ Composable ของกิจกรรมได้โดยใช้ Compose Testing API

Google ขอแนะนําให้คุณเรียกใช้ close ในกิจกรรมเมื่อการทดสอบเสร็จสมบูรณ์ ซึ่งจะล้างทรัพยากรที่เชื่อมโยงและปรับปรุงความเสถียรของการทดสอบ ActivityScenario ใช้ Closeable คุณจึงใช้ส่วนขยาย use เพื่อให้กิจกรรมปิดโดยอัตโนมัติได้

หรือจะใช้ createAndroidComposeRule เพื่อเปิดใช้งานกิจกรรมโดยอัตโนมัติก่อนการทดสอบแต่ละครั้ง จัดการการหยุดทำงาน และให้สิทธิ์เข้าถึงทั้งวิธีการทดสอบ UI ของ Compose และ ActivityScenario ที่อยู่เบื้องหลังก็ได้ ตัวอย่างต่อไปนี้แสดงวิธีกำหนดกฎและรับอินสแตนซ์ของสถานการณ์ จากกฎดังกล่าว

@RunWith(AndroidJUnit4::class)
class MyTestSuite {
    @get:Rule
    val composeTestRule = createAndroidComposeRule<MyActivity>()

    @Test fun testEvent() {
        val scenario = composeTestRule.activityRule.scenario
    }
}

ขับเคลื่อนกิจกรรมไปสู่สถานะใหม่

หากต้องการเปลี่ยนสถานะกิจกรรมเป็นสถานะอื่น เช่น CREATED หรือ STARTED ให้เรียกใช้ moveToState การดำเนินการนี้จำลองสถานการณ์ที่กิจกรรมของคุณหยุด หรือหยุดชั่วคราวตามลำดับ เนื่องจากถูกขัดจังหวะโดยแอปอื่นหรือการดำเนินการของระบบ

ตัวอย่างการใช้งาน moveToState ปรากฏในข้อมูลโค้ดต่อไปนี้

@RunWith(AndroidJUnit4::class)
class MyTestSuite {
    @Test fun testEvent() {
        launchActivity<MyActivity>().use { scenario ->
            scenario.moveToState(State.CREATED)
        }
    }
}

กำหนดสถานะกิจกรรมปัจจุบัน

หากต้องการพิจารณาสถานะปัจจุบันของกิจกรรมที่อยู่ระหว่างการทดสอบ ให้รับค่าของฟิลด์ state ภายในออบเจ็กต์ ActivityScenario การตรวจสอบสถานะของกิจกรรมที่อยู่ระหว่างการทดสอบจะมีประโยชน์อย่างยิ่ง หากกิจกรรมเปลี่ยนเส้นทางไปยังกิจกรรมอื่นหรือสิ้นสุดด้วยตัวเอง ดังที่แสดงในข้อมูลโค้ดต่อไปนี้

@RunWith(AndroidJUnit4::class)
class MyTestSuite {
    @Test fun testEvent() {
        launchActivity<MyActivity>().use { scenario ->
            scenario.onActivity { activity ->
              startActivity(Intent(activity, MyOtherActivity::class.java))
            }

            val originalActivityState = scenario.state
        }
    }
}

สร้างกิจกรรมใหม่

เมื่ออุปกรณ์มีทรัพยากรเหลือน้อย ระบบอาจทำลายกิจกรรม ซึ่งจะทำให้แอปต้องสร้างกิจกรรมนั้นใหม่เมื่อผู้ใช้กลับมาที่แอป หากต้องการจำลองเงื่อนไขเหล่านี้ ให้เรียกใช้ recreate

@RunWith(AndroidJUnit4::class)
class MyTestSuite {
    @Test fun testEvent() {
        launchActivity<MyActivity>().use { scenario ->
            scenario.recreate()
        }
    }
}

คลาส ActivityScenario จะรักษาสถานะอินสแตนซ์ที่บันทึกไว้ของกิจกรรมและ ออบเจ็กต์ใดก็ตามที่มีคำอธิบายประกอบโดยใช้ @NonConfigurationInstance โดยออบเจ็กต์เหล่านี้จะโหลด ลงในอินสแตนซ์ใหม่ของกิจกรรมภายใต้การทดสอบ

เรียกผลลัพธ์ของกิจกรรม

หากต้องการรับรหัสผลลัพธ์หรือข้อมูลที่เชื่อมโยงกับกิจกรรมที่เสร็จสมบูรณ์แล้ว ให้รับ ค่าของฟิลด์ result ภายในออบเจ็กต์ ActivityScenario การใช้ createAndroidComposeRule คุณจะทริกเกอร์การทำงานของ UI ที่สิ้นสุดกิจกรรมได้อย่างง่ายดาย ดังที่แสดงในข้อมูลโค้ดต่อไปนี้

@RunWith(AndroidJUnit4::class)
class MyTestSuite {
    @get:Rule
    val composeTestRule = createAndroidComposeRule<MyActivity>()

    @Test fun testResult() {
        composeTestRule.onNodeWithTag("finish_button").performClick()

        val scenario = composeTestRule.activityRule.scenario
        val resultCode = scenario.result.resultCode
        val resultData = scenario.result.resultData
    }
}

ทริกเกอร์การดำเนินการในกิจกรรม

เมธอดทั้งหมดภายใน ActivityScenario เป็นการเรียกที่บล็อก ดังนั้น API จึงกำหนดให้คุณเรียกใช้เมธอดเหล่านั้นในเธรดการตรวจสอบ

หากต้องการทริกเกอร์การดำเนินการในกิจกรรมที่อยู่ระหว่างการทดสอบ ให้ใช้ Compose Testing API เพื่อ โต้ตอบกับ Composable ดังนี้

@RunWith(AndroidJUnit4::class)
class MyTestSuite {
    @get:Rule
    val composeTestRule = createAndroidComposeRule<MyActivity>()

    @Test fun testEvent() {
        composeTestRule.onNodeWithText("Refresh").performClick()
    }
}

อย่างไรก็ตาม หากต้องการเรียกใช้เมธอดในกิจกรรมเอง คุณสามารถทำได้อย่างปลอดภัยโดยใช้ onActivity ดังนี้

@RunWith(AndroidJUnit4::class)
class MyTestSuite {
    @Test fun testEvent() {
        launchActivity<MyActivity>().use { scenario ->
            scenario.onActivity { activity ->
              activity.handleSwipeToRefresh()
            }
        }
    }
}

แหล่งข้อมูลเพิ่มเติม

ดูข้อมูลเพิ่มเติมเกี่ยวกับการทดสอบได้ที่แหล่งข้อมูลเพิ่มเติมต่อไปนี้

เอกสารประกอบ