penggunaan pytest dengan appium

Pytest: Memahami Cara Kerja Testing Framework (bagian 1)

Apa itu pytest?

icon Pytest

Adalah kerangka kerja dari pengujian pada kode python, bisa dibilang semua test framework (junit, testng, rspec, dkk) adalah jantung nya dari segala test automation framework, pytest bisa digunakan pada berbagai tipe dan level dari software testing, sebenarnya ada berbagai alternatif testing tools pada python yang lainya seperti uniitest ataupun nose, tapi banyak open source project yang mulai "hijrah" mengadopsi pytest karena fitur yang ada pada pytest yang menarik diantara yang lainya yaitu:

  • Mudah membuat kode test dari pengujian sederhana hingga pengujian kompeks tetap mudah menuliskan kode pengujiannya dengan pytest
  • Mudah dibaca
  • Mudah dipelajari
  • Kode yang Pythonic banget
  • Bahkan pytest bisa menjalankan kode pengujian yang ditulis dengan format unittest ataupun nose
  • Komunitas yang sangat aktif dan pengembangan yang terjaga

 


Post ini merupakan rangkaian post mengenai membuat automationt test dengan python

Daftar isinya:

  1. Belajar Python dari dasar
  2. Memahami cara kerja Pytest (bagian 1) <== Sekarang disini
  3. Mulai membuat automation test dengan Selenium
  4. Menemukan Element dengan locator strategi yang baik

 

Berikutnya akan kita belajar tentang penggunaan pytest dalam mengembangkan kerangka kerja (framework) pengujian otomatis (automated test) dalam bahasa pemrograman python, dengan menguasai kerangka kerja pengujian di python maka kamu akan dengan mudah mengkombinasikan automated test pada REST API, browser dengan selenium nya ataupun mobile apps dengan appium karena sesungguhnya mereka itu adalah library yang menjadi pelengkap pytest ini 😅 

Persiapan Pytest

Saya asumsikan python sudah terinstal di komputer kamu, dan tak diperlukan untuk tahu banyak tentang python itu sendiri, karena contoh yang akan saya tunjukan cuma kode sederhana bahkan bisa dibilang terlalu sederhana :D

Cara installnya cukup menjalankan command berikut pada terminal ataupun command line kamu

pip install pytest

lalu setelah installasi berhasil coba jalankan perintah:

pytest --help

jika installasi benar maka akan memunculkan informasi lengkap tentang cara penggunaan pytest pada command line

dokumentasi lebih lanjut bisa dilihat di https://docs.pytest.org/en/latest/ 

Menjalankan Pytest

Secara aturan (convention) di berbagai macam project pengujian, kode test harus ditaruh didalam directory (folder) /tests/, dan secara otomatis pytest akan menemukan dan mengeksekusi test yang ditemukan dalam proses test discovery seperti berikut:

  • Nama file mengandung nama "test_<sesuatu>.py" ataupun "<sesuatu>_test.py"
  • Test class yang dinamai "Test<Sesuatu>"
  • Test method/function yang diawali "test_<sesuatu>", dan menariknya, pytest tidak memerlukan sebuah file __init__.py disemua test directory seperti pada aplikasi python pada umumnya

cara menjalankan kode test:

$ ​​pytest​​ tests/menjalankan seluruh test pada directory /tests/
$ ​​pytest​​ tests/nama_file.pymenjalankan test hanya pada module "nama_file.py"
$ ​​pytest​​ tests/nama_file.py::TestClassmenjalankan test hanya pada class TestClass di module "nama_file.py"

$ ​​pytest​​ tests/nama_file::TestClass::test_method

atau jika bentuk test bukan dalam Class

$ ​​pytest​​ tests/nama_file::test_method

menjalankan test hanya di method tertentu saja, tidak menjalankan method lainnya

 

Marker

Penggunaan decorator @pytest.mark.<sesuatu> sangat memudahkan kita dalam mengelompokan test, ibarat tagging dari test, satu test bisa memiliki lebih dari satu mark, dan kitapun bisa mengeksekusi test berdasarkan mark tertentu, seperti berikut

$ ​​pytest​​ -m smoke

maka pytest akan mencari test mana saja yang memiliki tag @pytest.mark.smoke untuk dijalankan

Informasi lebih lanjut, kamu bisa akses dokumentasinya langsung di terminal dengan perintah

$ ​​pytest​​ --help

Menulis Test

Kurang lebih contoh kerangka kerja test pada pytest sebagai berikut:

struktur kode pytest pada umumnya

 

File test berada dibawah directory tests, dan pytest.ini adalah file optional, biasanya terkait dengan configurasi default cara menjalankan pytest, lalu pytest.py ini juga optional, bisa dianggap file ini berisikan dari "local plugin" karena semua kode yang ada disini bisa diakses oleh seluruh file test yang dijalankan, sehingga sangat cocok untuk menaruh kode yang bisa di reuse antar test

Pada kesempatan kali ini sebagai contoh sederhana dalam mencoba pytest, buatlah sebuah file /tests/test_math.py yang di dalamnya isinya sebagai berikut:

def test_pertambahan():
    assert 1 + 11 == 12
    
    
class TestHimpunan:
    def test_persamaan(self):
        assert (1,2,3) == (1,2,3)

lalu cara menjalankan nya pada terminal dengan perintah sebagai berikut:

pytest tests/test_math.py

Output yang dihasilkan kurang lebih seperti berikut:

output test berhasil

Ok kita bahas ya, pada contoh diatas saya menjalankan 2 test pada file test_math.py yaitu def test_pertambahan dan def test_persamaan, disini saya menunjukan bahwa pytest support bentuk kode pengujian yang dituliskan sebagai function mandiri atau method pada class, tidak ada perbedaan signifikan, hanya pengelompokan test saja menurut saya.

Dan jika ditilik lagi, jika test berjalan baik dan passed akan ditandai dengan simbol titik warna hijau (di windows gada warnanya) pada output console dan jika failed ditandai dengan huruf F warna merah, disertai dengan informasi pelengkapnya.

agar lebih jelas lagi mari kita coba membuat test gagal dengan mengubah nilai pada assertnya, dan agar tampilan output console lebih informatif, jalankan perintah pytest -v tests/test_math.py lalu perhatikan error message yang ditampilkan sebagai berikut

hasil menjalankan kode test yang ternyata failed :P

Ada berbagai macam jenis outcome dari sebuah test yang akan dihasilkan oleh pytest sebagai berikut:

  • PASSED (.) adalah test yang berjalan sebagaimana mestinya
  • FAILED (F) adalah test yang tidak berjalan seperti yang diharapkan
  • SKIPPED (s) adalah test yang tidak dijalankan (dilompati), kita bisa mengkonfigurasi test yang harus di lompati dengan menggunakan decorator @pytest.mark.skip() atau secara programatically
  • xfail (x): adalah test yang tidak seharusnya untuk pass, jadi secara eksplisit kita mengharapkan suatu test untuk failed, ditandai dengan decorator @pytest.mark.xfail()
  • XPASS (X): kurang lebih mirip xfail
  • ERROR (E) adalah exception yang terjadi diluar test function tersebut, bisa gara-gara fixture, di hook atau dari mis-configurasi

Ekspektasi

Pytest akan menggak exception yang tidak dihandle sebagai sebuah failure, pada saat statement assert dihadapkan kepada nilai False maka ia akan melempar exception dan langsung memberhentikan eksekusi program, jadi tidak akan dilanjutkan ke statement setelah assert yang failed tersebut

class TestHimpunan:
    def test_persamaan(self):
        assert (1,3,5) == (1,4,5)
        print('Bagian ini tidak akan dijalankan')

Tapi jika memang justru exception yang diharpkan maka bisa menggunakan pytest.raises

 

Contoh studi kasus JSON api kode post Indonesia

Contoh API test sederhana menggunakan pytest untuk menguji json api dari repo ini https://github.com/bachors/Kode-Pos-API yang memiliki aplikasi live di firebaseio

Kita buat file di tests/feature_kodepost/test_kodepos_indonesia.py, isinya

iimport requests 

def test_provinsi():
    list_provinsi = requests.get('https://kodepos-2d475.firebaseio.com/list_propinsi.json?print=pretty')
    data_prov = list_provinsi.json()
    assert len(data_prov) == 34
    assert data_prov.get('p9') == 'Jawa Barat'
    
def test_kotakab_jabar():
    list_kotakab = requests.get('https://kodepos-2d475.firebaseio.com/list_kotakab/p9.json?print=pretty')
    data_kotakab = list_kotakab.json()
    assert list_kotakab.status_code == 200
    assert data_kotakab.get('k60') == 'Tasikmalaya_typo'
    assert len(data_kotakab) == 21
    
def test_kodepos_tasik():
    list_keckel = requests.get('https://kodepos-2d475.firebaseio.com/kota_kab/k60.json?print=pretty')
    data_kodepos = list_keckel.json()
    assert list_keckel.status_code == 200
    assert len(data_kodepos) == 420
 

lalu cara menjalankannya dengan  command

➜ pytest -v tests/feature_kodepos

maka akan muncul output sebagai berikut

output menjalankan test kdoepos

Test nya sengaja saya buat failed, karena untuk melihat betapa cantiknya error log dari pytest jika terjadi masalah, apa yang menarik disini:

  • Informasi kesalahan yang jelas, contoh diatas ada typo pada string yang dibandingkan (assert) maka ditunjukan kelebihan character dengan tanda plus
  • test dijalankan sesuai dengan urutan penulisan test pada file, jadi dieksekusi dari atas kebawah
  • walaupun test ke-2 failed, tetap melanjutkan ekseskusi test ke-3, (stop ekseskusi karena throw exception hanya pada scope test function, jadi dari failed tersebut tidak akan melanjutkan ekseskusi baris statement berikutnya tapi langsung pindah ke test berikutnya)

Yuk kita bermain dengan kode test diatas, berikutnya kita ubah kode test sebagai berikut

Kita tambahkan decorator xfail di method yg gagal menjadi seperti ini

@pytest.mark.xfail
def test_kotakab_jabar():
...

Lalu jalankan kembali testnya dan outputnya sekarang berbeda

semua hasil passed dengan catatan 1 xfail

Nah terlihat bahwa sekarang semua test hijau (passed) dengan catatan ada 1 test yang memang expected failed (xfailed)

Pytest Fixtures

Nah bagian ini sebenarnya yang menurut saya paling keren dari pytest, tapi berhubung postingan kali ini sudah cukup panjang, maka informasi lebih lanjut terkait fixture akan disambung di post selanjutnya ya, dengan contoh framework pada web ui testing

Bersambung ...

This article was updated on 20 Mei 2020

Comments