اختبار أنشطة تطبيقاتك

تعمل الأنشطة كحاويات لكل تفاعل يجريه المستخدم داخل تطبيقك، لذا من المهم اختبار سلوك أنشطة تطبيقك أثناء الأحداث على مستوى الجهاز مثل ما يلي:

  • يعمل تطبيق آخر، مثل تطبيق الهاتف على الجهاز، على مقاطعة نشاط تطبيقك.
  • يدمر النظام نشاطك ويعيد إنشائه.
  • يضع المستخدم نشاطك في بيئة نوافذ جديدة، مثلاً نافذة ضمن النافذة (PIP) أو نافذة متعددة.

وعلى وجه الخصوص، من المهم التأكّد من أنّ نشاطك يتضمّن سلوكًا صحيحًا استجابةً للأحداث الموضّحة في دورة حياة النشاط.

يشرح هذا الدليل كيفية تقييم قدرة تطبيقك على الحفاظ على سلامة البيانات وتقديم تجربة جيدة للمستخدم من خلال انتقال أنشطة التطبيق إلى مراحل مختلفة من نشاطه.

Drive من حالة نشاط

يتضمن أحد الجوانب الرئيسية لاختبار أنشطة التطبيق وضع أنشطة التطبيق في حالات معينة. لتحديد هذا الجزء "المعطى" من الاختبارات، استخدِم مثيلات ActivityScenario، وهو جزء من مكتبة AndroidX Test. باستخدام هذا الفصل، يمكنك وضع نشاطك في حالات تحاكي الأحداث على مستوى الجهاز.

ActivityScenario هي واجهة برمجة تطبيقات من عدّة منصات يمكنك استخدامها في اختبارات الوحدات المحلية واختبارات الدمج على الجهاز على حد سواء. على جهاز حقيقي أو افتراضي، يوفّر ActivityScenario أمان سلسلة المحادثات، ويقوم بمزامنة الأحداث بين سلسلة تعليمات قياس حالة الاختبار وسلسلة المحادثات التي تشغّل نشاطك قيد الاختبار.

تكون واجهة برمجة التطبيقات مناسبة بشكل خاص لتقييم سلوك نشاط يخضع للاختبار عند تدميره أو إنشائه. يعرض هذا القسم حالات الاستخدام الأكثر شيوعًا المرتبطة بواجهة برمجة التطبيقات هذه.

إنشاء نشاط

لإنشاء النشاط قيد الاختبار، أضِف الرمز المعروض في المقتطف التالي:

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

بعد إنشاء النشاط، ينقل ActivityScenario النشاط إلى الحالة RESUMED. تشير هذه الحالة إلى أنّ نشاطك قيد التشغيل ويظهر للمستخدمين. وفي هذه الحالة، يمكنك التفاعل مع عناصر View لنشاطك باستخدام اختبارات Espresso UI.

تنصحك Google بالاتصال بـ close عند اكتمال النشاط عند اكتماله. يؤدي ذلك إلى تنظيف الموارد ذات الصلة وتحسين استقرار اختباراتك. ينفِّذ ActivityScenario الإجراء Closeable، لذا يمكنك تطبيق الإضافة use، أو try-with-resources في لغة البرمجة Java، بحيث يتم إغلاق النشاط تلقائيًا.

بدلاً من ذلك، يمكنك استخدام ActivityScenarioRule للاتصال تلقائيًا برقم ActivityScenario.launch قبل كل اختبار وActivityScenario.close عند إنهاء الاختبار. يوضح المثال التالي كيفية تحديد قاعدة والحصول على مثيل لسيناريو منها:

@RunWith(AndroidJUnit4::class)
class MyTestSuite {
    @get:Rule var activityScenarioRule = activityScenarioRule<MyActivity>()

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

نقل النشاط إلى حالة جديدة

لتوجيه النشاط إلى حالة مختلفة، مثل CREATED أو STARTED، استدعِ moveToState(). يحاكي هذا الإجراء موقفًا يتم فيه إيقاف نشاطك أو إيقافه مؤقتًا، على التوالي، بسبب مقاطعة تطبيق آخر أو إجراء نظام.

يظهر مثال على استخدام moveToState() في مقتطف الرمز التالي:

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

تحديد حالة النشاط الحالية

لتحديد الحالة الحالية لنشاط قيد الاختبار، احصل على قيمة الحقل 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، كما هو موضّح في مقتطف الرمز التالي:

@RunWith(AndroidJUnit4::class)
class MyTestSuite {
    @Test fun testResult() {
        launchActivity<MyActivity>().use {
            onView(withId(R.id.finish_button)).perform(click())

            // Activity under test is now finished.

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

تشغيل الإجراءات في النشاط

تحظر جميع الطرق ضمن ActivityScenario الطلبات، لذا تتطلب منك واجهة برمجة التطبيقات تشغيلها في سلسلة الأدوات.

لتشغيل الإجراءات في نشاطك قيد الاختبار، استخدِم أدوات مطابقة طرق عرض Espresso للتفاعل مع العناصر في طريقة العرض:

@RunWith(AndroidJUnit4::class)
class MyTestSuite {
    @Test fun testEvent() {
        launchActivity<MyActivity>().use {
            onView(withId(R.id.refresh)).perform(click())
        }
    }
}

إذا كنت بحاجة إلى طلب طريقة في النشاط نفسه، يمكنك إجراء ذلك بأمان من خلال تنفيذ ActivityAction:

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