19 lines | 1.9 KB

AGENTS.md — Django

  • Follow PEP 8; format with black (88-char code lines, 79 for docs/comments). 4-space Python indent, 2-space HTML.
  • underscore_case for variables/functions/methods, InitialCaps for classes. Views take request as the first arg.
  • Sort imports with isort: future → stdlib → third-party → other Django → local → try/except. Absolute for Django, one-dot relative for local.
  • Don't use f-strings for translatable strings; mark strings for i18n and use format().
  • Models: lowercase underscore field names; class Meta after fields; order is fields → managers → Meta → __str__save()get_absolute_url() → custom methods.
  • Avoid N+1: select_related() for FK/OneToOne, prefetch_related() for ManyToMany and reverse relations.
  • QuerySets are lazy and cache once evaluated — store and reuse them; don't re-query in loops.
  • Prefer update(), bulk_create(), bulk_update(), F() expressions, and annotate() over per-object save() loops. Use values()/only() to fetch less.
  • Use the ORM for SQL safety; use raw()/extra()/RawSQL() sparingly and escape user input.
  • Never disable CSRF ({% csrf_token %} + CsrfViewMiddleware); avoid @csrf_exempt unless required.
  • Let template auto-escaping handle XSS; be careful with mark_safe/safe/autoescape-off and stored HTML.
  • Set ALLOWED_HOSTS; read host via request.get_host(), not request.META.
  • Production: DEBUG = False, secret SECRET_KEY, HTTPS with SECURE_SSL_REDIRECT, secure cookies, and HSTS.
  • Keep clickjacking (X-Frame-Options) protection on; validate input through forms; limit upload sizes.
  • Never read django.conf.settings at module import time — use lazy indirection (LazyObject, lazy(), lambda).
  • Add Meta.indexes/db_index for frequently filtered fields; profile with QuerySet.explain() before optimizing.