Python ve birim testleri

Ffe7cce8b26d88cb96c8db8df021b5c7?s=47 Emre Yılmaz
February 01, 2017

Python ve birim testleri

Ffe7cce8b26d88cb96c8db8df021b5c7?s=128

Emre Yılmaz

February 01, 2017
Tweet

Transcript

  1. BİRİM TESTLERİ VE PYTHON EMRE YILMAZ, OCAK ‘17

  2. BİRİM TESTLERİ ▸ Kodun belirli bölümlerini -birimlerini- test eden/çalıştıran kod

    bütünü. ▸ Doğası gereği hiçbir bağımlılığı olamaz. ▸ unit (birim), bir uygulamanın test edilebilir en küçük parçacığını ifade eder. Bu bir fonksiyon, sınıf, metod olabilir.)
  3. “WHENEVER YOU ARE TEMPTED TO TYPE SOMETHING INTO A PRINT

    STATEMENT OR A DEBUGGER EXPRESSION, WRITE IT AS A TEST INSTEAD.” Martin Fowler BİRİM TESTLERİ
  4. NE ZAMAN UNİT TEST OLMAZ? ▸ Test, çalışmak için kendinden

    daha büyük bir şeye ihtiyaç duyuyorsa “birim” test olmaktan çıkar.
 ▸ Örneğin, test çalışmak için 3. parti bir API çıktısına ihtiyaç duyuyorsa bu bir “entegrasyon testi” olur. ▸ Ya da tüm bir uygulama belirli kurallara göre, birbirine bağımlı senaryolarla test ediliyorsa “acceptance” test olur.
  5. BİRİM TESTLERİ NE İŞİMİZE YARAR? ▸ Geliştirme sırasında hataları tespit

    edebilmek için. ▸ Kodun tasarımı için bir araç. (TDD* ile kodlamadan önce dizayn etmek şart.) ▸ Bakımı yapılabilir kod geliştirmek için şart. ▸ * TDD: Test Driven Development (Test Güdümlü Programlama.)
  6. BİRİM TESTLERİ NE İŞİMİZE YARAR? ▸ Uygulamanın sorunsuz çalıştığını garanti

    etmez. Her birim sorunsuz çalışıyor ve tüm testler %100 coverage ile geçiyor olabilir, ama bu birimler bir arada doğru çalışmıyor olabilir. ▸ Testleri de yazan insanlar olduğu için ve insanlar her problemli durumu düşünemediği için %100 bug-free bir yazılım garanti etmez ama içiniz rahat, temiz, bakımı yapılabilir bir kod tabanı vaat eder.
  7. METGLOBAL’DE BİRİM TESTLERİ

  8. BEST PRACTICES ▸ Tek seferde tek birim test edin. ▸

    Her test kendi içinde bağımsız olmalı. Diğer testlerle ‘state’ paylaşmamalı. ▸ External servisler ve bağımlılıklar mock’lanmalı. ▸ Her test’in ismi, test ettiği birimi açıklamalı. ▸ Yazdığınız kod test edilebilir olmalı. (Django request’i kullanan bir metodu test etmek zor.)
  9. HIZLI BİR BAŞLANGIÇ ▸ pytest kütüphanesi ▸ Standart kütüphanedeki unittest

    modülünden daha rahat ve basit bir kütüphane. ▸ Sadece assert ile birim testi ihtiyaçlarının büyük kısmını karşılayabilirsiniz. (assertBilmemne ezberlemenize gerek yok.) ▸ kurulum: pip install pytest
  10. İLK TESTİMİZİ YAZALIM ▸ Bir iş görüşmesinde “palindrome” ne anlama

    gelir anlatıldı. Bir string’in palindrome olup olmadığını anlayan ve duruma göre True/False dönen bir fonksiyon yazmanız istendi.
 ▸ def is_palindrome(text):
 return True/False
  11. CODE COVERAGE ▸ Birim testlerin, test edilen modülün ne kadarını

    karşıladığını belirten bir ölçüm. Genelde yüzdelik dilimlerle ifade edilir. (%77 gibi.) ▸ pip install pytest-cov
 

  12. WORKSHOP ▸ Verilen numaranın asal olup olmadığını söyleyen basit bir

    fonksiyon: is_prime
 
 def is_prime(number):
 """
 Checks a number is a prime or not.
 Returns bool.
 """
 if number < 2:
 return False
 for i in range(2, number):
 if number % i == 0:
 return False
 
 return True

  13. WORKSHOP ▸ Atölye: ▸ https://github.com/metglobal/python-unit-testing- workshop/tree/master/solutions/prime_number ▸ deposunu yerelinize çekip

    testlerini yazıp pull request açınız. testlerinizi barındıran dosya, tests_ad_soyad.py şeklinde olmalıdır.

  14. MOCKING (SAHTE NESNELER YARATMA) ▸ external objeler, metodları taklit eden,

    onlar gibi davranan objeler yaratmak mümkün. ▸ metodun dönüş değeri, ne kadar saniye süreceği dahil her şey kontrol edilebilir. ▸ pip install mock (py3k’da standart kütüphanede var.) ▸ from mock import MagicMock
 reservation = MagicMock()
 reservation.cancel.return_value = 'cancelled'
 print reservation.cancel(booking_id='x', ref_no=15)
  15. LET’S PATCH ALL THE THINGS! ▸ External bağımlılıkları mock objeleriyle

    patchleyip unit-test’ler çalışırken dışa olan bu bağımlılığı ‘mock’layabiliriz. ▸ Hem birim testler hızlı çalışır, hem de hakikaten ‘birim’ test yapmış oluruz. Mesela, kodun bir aşamasında requests kütüphanesiyle bir API sistemine istek atılıyor diyelim. ▸ pip install pytest-mock ▸ def test_api(mocker):
 mocked_get = mocker.patch.object(requests, 'get')
 mocked_get.return_value.text = "NOTOK"
 response_text = requests.get(‘https://api2.hotelspro.com/api/v2/ping').text
 assert '"Ok"' == response_text
  16. Sorular?