فصل ۸: تست، استقرار و پروژه‌ی پایانی

کلینیک خطاهای رایج جنگو: علت و درمان

خطا را بخوانید، نه این‌که فقط گوگل کنید

بیشتر خطاهای جنگو پیام دقیقی دارند؛ مشکل این است که ما پیام را کامل نمی‌خوانیم. این درس پرتکرارترین خطاهایی را جمع کرده که در پروژه‌های واقعی، به‌خصوص هنگام اولین استقرار، دیده می‌شوند.

خطاعلت رایجدرمان
TemplateDoesNotExistقالب در مسیر مورد انتظار نیست یا DIRS تنظیم نشدهپیام «Template-loader postmortem» را بخوانید؛ مسیرهای بررسی‌شده را نشان می‌دهد. TEMPLATES["DIRS"] = [BASE_DIR / "templates"] و پوشه‌ی templates/<app>/ داخل اپ
NoReverseMatchنام url یا namespace اشتباه، یا آرگومان جاافتاده/خالیمتغیر خالی مثل pk="" را بررسی کنید؛ namespace را با app_name تطبیق دهید
static در DEBUG=False کار نمی‌کندrunserver فقط با DEBUG=True static سرو می‌کندcollectstatic + WhiteNoise یا location در nginx
403 CSRF verification failed پشت پراکسیCSRF_TRUSTED_ORIGINS بدون scheme، یا نبود X-Forwarded-Protohttps:// در CSRF_TRUSTED_ORIGINS و SECURE_PROXY_SSL_HEADER
Conflicting migrations detectedدو migration هم‌شماره از دو شاخهmakemigrations --merge
no such table / relation does not existmigrate اجرا نشده، یا migration اپ ساخته نشدهshowmigrations؛ بعد makemigrations همان اپ و migrate
DisallowedHostدامنه یا IP در ALLOWED_HOSTS نیستافزودن دامنه (بدون http و پورت)
RuntimeWarning: naive datetimedatetime.now() با USE_TZ=Truetimezone.now() یا make_aware
ImproperlyConfigured: SECRET_KEY.env خوانده نشده؛ معمولاً مسیر اشتباه در systemdEnvironmentFile و load_dotenv(BASE_DIR / ".env")
502 Bad Gatewaygunicorn بالا نیامده یا سوکت در دسترس nginx نیستjournalctl -u carpet و دسترسی www-data به سوکت
pip timeout / 403 در ایرانتحریم یا اختلال شبکهمیرور داخلی PyPI با pip config set global.index-url

روش عیب‌یابی گام‌به‌گام

# ۱. پیکربندی سالم است؟
python manage.py check
python manage.py check --deploy
# ۲. وضعیت migrationها
python manage.py showmigrations | grep "\[ \]"
# ۳. آدرس به کدام View می‌رسد؟
python manage.py shell -c "from django.urls import resolve; print(resolve('/orders/42/'))"
# ۴. لاگ سرویس‌ها روی سرور
journalctl -u carpet -n 100 --no-pager
sudo tail -n 50 /var/log/nginx/error.log

وقتی DEBUG=False است و خطا را نمی‌بینید

هرگز برای دیدن خطا DEBUG را روی سرور روشن نکنید. به‌جایش ADMINS را تنظیم کنید تا خطاهای 500 ایمیل شوند، لاگر django.request را در سطح ERROR به فایل بفرستید، یا یک سرویس گزارش خطا مثل Sentry (نسخه‌ی self-hosted برای شرایط تحریم) نصب کنید.

نکته‌هایی که کمتر کسی می‌داند

  • اگر TemplateDoesNotExist برای قالبی می‌آید که مطمئنید وجود دارد، به نام قالب داخل پیام دقت کنید: ListView بدون template_name دنبال orders/order_list.html می‌گردد، نه list.html.
  • NoReverseMatch با پیام «with arguments ('',)» یعنی url درست است اما مقدار ارسالی خالی بوده؛ معمولاً شیء هنوز ذخیره نشده و pk ندارد.
  • «no such table: django_session» در اولین اجرا یعنی حتی migrationهای خود جنگو اجرا نشده‌اند؛ یک migrate ساده کافی است.
  • خطای «Apps aren't loaded yet» معمولاً یعنی در یک اسکریپت مستقل قبل از django.setup() مدل import کرده‌اید، یا در models.py یک import حلقوی دارید.
  • تغییرات کد روی سرور بدون systemctl reload carpet اعمال نمی‌شوند؛ gunicorn کد را فقط هنگام شروع worker بارگذاری می‌کند و «کد را عوض کردم ولی فرقی نکرد» از همین است.

برای ذخیره‌ی پیشرفت و شرکت در آزمون، وارد شوید — رایگان است.