Pengujian lokal berjalan langsung di workstation Anda sendiri, bukan di emulator atau perangkat Android. Oleh karena itu, Java Virtual Machine (JVM) lokal Anda digunakan, bukan perangkat Android untuk menjalankan pengujian. Pengujian lokal memungkinkan Anda mengevaluasi logika aplikasi dengan lebih cepat. Namun, tidak dapat berinteraksi dengan framework Android akan menyebabkan batasan pada jenis pengujian yang dapat Anda jalankan.
Pengujian unit memverifikasi perilaku bagian kecil kode, unit yang sedang diuji. Hal itu dilakukan dengan mengeksekusi kode tersebut dan memeriksa hasilnya.
Pengujian unit biasanya sederhana, tetapi penyiapannya dapat menjadi masalah jika unit yang sedang diuji tidak didesain dengan mempertimbangkan kemudahan pengujian:
- Kode yang ingin Anda verifikasi harus dapat diakses dari pengujian. Misalnya, Anda tidak dapat menguji metode pribadi secara langsung. Sebagai gantinya, Anda akan menguji class menggunakan API publiknya.
- Untuk menjalankan pengujian unit secara isolasi, dependensi unit yang sedang diuji harus diganti dengan komponen yang Anda kontrol, seperti palsu atau pengujian ganda lainnya. Hal ini akan bermasalah jika kode Anda bergantung pada framework Android.
Untuk mempelajari strategi pengujian unit umum di Android, baca Yang harus diuji.
Lokasi tes lokal
Secara default, file sumber untuk pengujian unit lokal ditempatkan di
module-name/src/test/
. Direktori ini sudah ada saat Anda membuat project
baru menggunakan Android Studio.
Menambahkan dependensi pengujian
Anda juga harus mengonfigurasi dependensi pengujian untuk project Anda agar dapat menggunakan API standar yang disediakan oleh framework pengujian JUnit.
Untuk melakukannya, buka file build.gradle
modul aplikasi dan tentukan library
berikut sebagai dependensi. Gunakan fungsi testImplementation
untuk menunjukkan
bahwa fungsi tersebut berlaku untuk set sumber pengujian lokal, dan bukan aplikasi:
dependencies {
// Required -- JUnit 4 framework
testImplementation "junit:junit:$jUnitVersion"
// Optional -- Robolectric environment
testImplementation "androidx.test:core:$androidXTestVersion"
// Optional -- Mockito framework
testImplementation "org.mockito:mockito-core:$mockitoVersion"
// Optional -- mockito-kotlin
testImplementation "org.mockito.kotlin:mockito-kotlin:$mockitoKotlinVersion"
// Optional -- Mockk framework
testImplementation "io.mockk:mockk:$mockkVersion"
}
Membuat class pengujian unit lokal
Anda menulis class pengujian unit lokal sebagai class pengujian JUnit 4.
Untuk melakukannya, buat class yang berisi satu atau beberapa metode pengujian, biasanya dalam
module-name/src/test/
. Sebuah metode pengujian dimulai dengan anotasi @Test
dan
berisi kode untuk dijalankan serta memverifikasi satu aspek komponen yang
ingin Anda uji.
Contoh berikut menunjukkan cara mengimplementasikan class pengujian unit lokal. Metode
pengujian emailValidator_correctEmailSimple_returnsTrue()
mencoba memverifikasi
isValidEmail()
yang merupakan metode dalam aplikasi. Fungsi pengujian akan menampilkan
benar jika isValidEmail()
juga menampilkan benar.
Kotlin
import org.junit.Assert.assertFalse import org.junit.Assert.assertTrue import org.junit.Test class EmailValidatorTest { @Test fun emailValidator_CorrectEmailSimple_ReturnsTrue() { assertTrue(EmailValidator.isValidEmail("name@email.com")) } }
Java
import org.junit.Test; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; class EmailValidatorTest { @Test public void emailValidator_CorrectEmailSimple_ReturnsTrue() { assertTrue(EmailValidator.isValidEmail("name@email.com")); } }
Anda harus membuat pengujian dapat dibaca yang mengevaluasi apakah komponen dalam
aplikasi menampilkan hasil yang diharapkan. Sebaiknya gunakan library pernyataan seperti
junit.Assert, Hamcrest, atau
Truth. Cuplikan di atas adalah contoh cara menggunakan
junit.Assert
.
Library Android tiruan
Saat menjalankan pengujian unit lokal, Android Gradle Plugin menyertakan library yang berisi semua API framework Android, yang sesuai dengan versi yang digunakan dalam project Anda. Library ini menyimpan semua metode publik dan class API tersebut, tetapi kode di dalam metode telah dihapus. Jika salah satu metode diakses, pengujian akan menampilkan pengecualian.
Hal ini memungkinkan pengujian lokal dibuat saat mereferensikan class dalam framework
Android seperti Context
. Yang lebih penting, ini memungkinkan Anda menggunakan framework
tiruan dengan class Android.
Meniru dependensi Android
Masalah yang umum terjadi adalah menemukan bahwa sebuah class menggunakan resource string. Anda bisa
memperoleh resource string dengan memanggil metode getString()
di class
Context
. Namun, pengujian lokal tidak dapat menggunakan Context
atau metodenya karena
termasuk dalam framework Android. Idealnya, panggilan ke getString()
akan
dipindahkan dari class, tetapi hal ini tidak selalu praktis. Solusinya adalah dengan
membuat tiruan atau stub Context
yang selalu menampilkan nilai yang sama saat
metode getString()
dipanggil.
Dengan library Android Mockable dan framework tiruan seperti Mockito atau MockK, Anda dapat memprogram perilaku tiruan class Android dalam pengujian unit.
Untuk menambahkan objek tiruan ke pengujian unit lokal menggunakan Mockito, ikuti model pemrograman ini:
- Sertakan dependensi library Mockito dalam file
build.gradle
, seperti yang dijelaskan dalam Menyiapkan lingkungan pengujian Anda. - Di awal definisi class pengujian unit, tambahkan anotasi
@RunWith(MockitoJUnitRunner.class)
. Anotasi ini memberi tahu runner pengujian Mockito untuk memvalidasi bahwa penggunaan framework sudah benar dan menyederhanakan inisialisasi objek tiruan Anda. - Untuk membuat objek tiruan untuk dependensi Android, tambahkan anotasi
@Mock
sebelum deklarasi kolom. - Untuk menghentikan perilaku dependensi, Anda dapat menentukan kondisi dan menampilkan nilai jika kondisi terpenuhi dengan menggunakan metode
when()
danthenReturn()
.
Contoh berikut menunjukkan cara membuat pengujian unit yang menggunakan objek
Context
tiruan di Kotlin yang dibuat dengan Mockito-Kotlin.
import android.content.Context
import org.junit.Assert.assertEquals
import org.junit.Test
import org.junit.runner.RunWith
import org.mockito.Mock
import org.mockito.junit.MockitoJUnitRunner
import org.mockito.kotlin.doReturn
import org.mockito.kotlin.mock
private const val FAKE_STRING = "HELLO WORLD"
@RunWith(MockitoJUnitRunner::class)
class MockedContextTest {
@Mock
private lateinit var mockContext: Context
@Test
fun readStringFromContext_LocalizedString() {
// Given a mocked Context injected into the object under test...
val mockContext = mock<Context> {
on { getString(R.string.name_label) } doReturn FAKE_STRING
}
val myObjectUnderTest = ClassUnderTest(mockContext)
// ...when the string is returned from the object under test...
val result: String = myObjectUnderTest.getName()
// ...then the result should be the expected one.
assertEquals(result, FAKE_STRING)
}
}
Untuk mempelajari penggunaan framework Mockito lebih lanjut, lihat referensi
Mockito API dan class SharedPreferencesHelperTest
dalam
kode contoh. Coba juga Android Testing Codelab.
Error: "Metode ... tidak ditiru"
Library Android tiruan akan menampilkan pengecualian jika Anda mencoba mengakses salah satu
metodenya dengan pesan Error: "Method ... not mocked
.
Jika pengecualian yang ditampilkan bermasalah untuk pengujian, Anda dapat mengubah
perilakunya sehingga metode akan menampilkan null atau nol, bergantung pada
jenis nilai yang ditampilkan. Untuk melakukannya, tambahkan konfigurasi berikut di file
build.gradle
level atas project Anda di Groovy:
android {
...
testOptions {
unitTests.returnDefaultValues = true
}