🧪 فصل ۱۹: آشنایی با تستنویسی (Testing) در پایتون

۱۹.۱ چرا تستنویسی مهم است؟
حتی حرفهایترین برنامهنویسها هم گاهی اشتباه میکنند!
با تستنویسی میتوانیم:
- مطمئن شویم کدهایمان همانطور که انتظار داریم اجرا میشوند.
- بعداً با تغییر کد، اطمینان پیدا کنیم کدهای قبلی خراب نمیشوند (regression).
- کیفیت و اطمینان پروژه را افزایش بدهیم.
تستنویسی مخصوص برنامههای بزرگ نیست — پروژههای کوچک هم همیشه از داشتن تست بهرهمند میشوند.
۱۹.۲ انواع تست در پایتون
- واحدی (Unit test): بررسی یک تکه کوچک از کد (یک تابع)
- تستی یکپارچه (Integration test): امتحان چند بخش جداگانه با هم
- تست عملکردی یا کاربردی (Functional): نگاه از دید کاربر نهایی
در این فصل روی تست واحدی (unit test) تمرکز داریم. ابزار اصلی:
unittest (کتابخانه استاندارد پایتون)
۱۹.۳ ساختار یک تست ساده
اول با یک مثال ساده شروع کنیم:
گام ۱: تابع اصلی را بنویس
فایل calc.py:
def add(a, b):
return a + b
گام ۲: فایل تست بساز
فایل test_calc.py:
import unittest
from calc import add
class TestAdd(unittest.TestCase):
def test_add(self):
self.assertEqual(add(2, 3), 5)
self.assertEqual(add(-1, 1), 0)
if __name__ == '__main__':
unittest.main()
گام ۳: اجرای تستها
ترمینال:
python test_calc.py
اگر test passed بود یعنی برگ سبزی به کدت تعلق میگیرد!
اگر خطا داشته باشی، علت دقیق در خروجی نشان داده میشود.
۱۹.۴ تست چند حالت و خطا
تست، فقط “حالت درست” نیست! حالتهای عجیـب و ورودی نادرست را هم تست میکنیم.
def test_add_strings(self):
with self.assertRaises(TypeError):
add("5", 2)
۱۹.۵ نوشتن تست برای چند تابع
فرض کن در بدنه پروژه این توابع هستند:
def multiply(a, b):
return a * b
در کلاس تست:
def test_multiply(self):
self.assertEqual(multiply(2, 5), 10)
self.assertEqual(multiply(0, 10), 0)
۱۹.۶ ساختار استاندارد پروژه با تست
پیشنهاد حرفهای:
project/
│
├── calc.py
├── test_calc.py
یا اگر پروژه بزرگتر شد:
project/
├── src/
│ └── main.py
└── tests/
└── test_main.py
۱۹.۷ ابزارهای تست پیشرفته
- pytest: ابزار حرفهایتر و سادهتر (نصب: pip install pytest)
- ساخت تستهای سریع (فقط با assert!)
- پشتیبانی عالی از پارامتر، fixture و گزارش خطای زیبا
مثال خیلی ساده با pytest:
from calc import add
def test_add():
assert add(2, 2) == 4
اجرا:
pytest
۱۹.۸ نکات حرفهای تستنویسی
- برای هر تابع، چندین تست بنویس (حالت درست و نادرست)
- هر باگ قدیمی را یک تست پایدار کن تا تکرار نشود.
- اگر کد تیمی مینویسی، قبل از ادغام هر فیچر، تستها را اجرا کن.
- پوشش تست (coverage) ابزار خوبی برای سنجش میزان تستشدن کدهاست (پیشنهاد: coverage.py)
تمرین عملی (برای خودآزمایی):
۱. دو تابع ساده بنویس (مثلاً تقسیم و فاکتوریل) و برایشان حداقل ۳ تست بنویس.
۲. یک ورودی نامعتبر را هم بررسی کن تا تست خطا داشته باشی (مثل تقسیم بر صفر).
جمعبندی
- تستنویسی عادت فوقالعاده برای هر برنامهنویس است.
- حتی پروژههای کوچک بدون تست هم میتوانند سرنوشتشان را به دست باگ بسپارند!
- یونیت تست در پایتون یک مهارت ضروری شغلی است.