4.1Web back end with Django
The essentials in 30 seconds
- Django = “batteries included”: ORM (database handled as Python objects), migrations (evolution without manual SQL), auto-generated admin and auth provided out of the box.
- MVT flow:
models.py(data) →urls.py(routes) →views.py(logic) →.htmltemplate (display);makemigrations + migrateafter each model. - Nabil's reflex: embrace the MVT conventions instead of fighting them — Django imposes a constraining structure at first, a life-saving one afterwards.
Running mini-case — Nabil exposes his sales in Algiers
Nabil, junior data analyst in Algiers, spends his days resending the same sales CSV file to his colleagues. He decides to build a mini back office with Django: a Vente model (city, amount, date), migrations that create the table without SQL, and the auto-generated admin where the team views and filters sales without bothering him. In one week, his weekly CSV becomes an application everyone queries alone. First milestone of the running thread: from the analyst who sends files to the developer who exposes a service.
This same case returns in the lesson, the diagram, the script and the 48h challenge — and continues in 4.2, 4.3, 4.4 and 4.5.
1. “Batteries included” Django and MVT
Django is Python's complete web framework: it provides out of the box the administration (generated back office), the ORM (database handled as Python objects), authentication (accounts, permissions) and security (CSRF, XSS, injections). Its organisation is called MVT: the Model (models.py) describes the data, the View (views.py) holds the logic, the Template (.html) displays — routing (urls.py) linking URLs and views. Like Nabil, embrace these conventions: constraining at first, life-saving afterwards.
2. ORM, migrations and admin: the productive trio
The ORM turns your Python classes into tables: class Vente(models.Model) with fields (CharField, DecimalField, DateField) becomes a table, and Vente.objects.filter(ville="Alger") replaces the SELECT — with no manual SQL. Migrations version every model change: python manage.py makemigrations then migrate, and the database evolves cleanly, in a team as in production. The admin (enabled via createsuperuser, on /admin) offers from the first minutes a back office to view and fix data. Nabil earns his first service to the team there.
When to choose Django? Server-rendered pages + accounts + back office → Django. Pure JSON consumed by a separate front end → rather a lightweight API (see 4.2). And even with the ORM, SQL basics remain useful to optimise and understand what happens under the hood.
🔎 Concrete example — 🔎 Concrete example — Nabil's sales in MVT
Nabil's four moves, with the real APIs:
models.py → class Vente(models.Model): ville, montant, date
shell → makemigrations + migrate (table created, no SQL)
urls.py → path('ventes/', vues.liste_ventes)
views.py → Vente.objects.filter(ville="Alger") → template
Reading: model, route, view, template — each in its place.
Lesson: the admin exposes these sales with no back office to code.
Section vocabulary
- Django
- Complete Python web framework (“batteries included”): admin, ORM, authentication and security provided from the start.
Simple example: Nabil builds his sales back office there in one week.
What it is not: a pile of scripts with no structure or accounts.
Reflex: pages + accounts + admin? think Django first.
- MVT (Model-View-Template)
- Django code organisation: Model (data), View (logic), Template (HTML display), linked by urls.py routing.
Simple example: Nabil's sales: Vente model, liste_ventes view, ventes.html template.
What it is not: a single script mixing SQL, logic and HTML.
Reflex: for each file, ask: data, logic or display?
- ORM
- Handling the database via Python objects (Vente.objects.filter(...)) instead of writing SQL.
Simple example: Nabil filters Algiers sales without writing a SELECT.
What it is not: SQL concatenated with variables in the code.
Reflex: read the generated queries when a page slows down.
- Migration
- File translating your model changes into database changes (makemigrations + migrate).
Simple example: Nabil adds the date field: one migration evolves the table everywhere.
What it is not: ALTER TABLE statements done by hand in production.
Reflex: never change the structure outside a migration.
In practice — In practice — Discover Django and its admin
- In a venv, install Django (pip install django) and create a project: “django-admin startproject monsite”, then an app “python manage.py startapp ventes”.
- Declare a model (e.g. Vente: city, amount, date), then run “makemigrations” and “migrate”: watch the table created without SQL.
- Create a superuser (“createsuperuser”), run “runserver” and explore the admin: add and filter rows.
- Add a URL, a view querying the ORM and a template displaying the list.
Ready-to-say script — presenting your back office (30 s)
“This is Nabil: our sales live in a Django model, the database evolves through migrations, and the team views them in the admin without asking me for a CSV. URLs, views and templates follow MVT: everyone knows where to look.”
Say in a team check-in; show the admin live.
Copy-paste template — mini Django app (tested code)
# ventes/models.py
from django.db import models
class Vente(models.Model):
ville = models.CharField(max_length=80)
montant = models.DecimalField(max_digits=10, decimal_places=2)
date = models.DateField()
def __str__(self):
return f"{self.ville} — {self.montant}"
# ventes/views.py
from django.shortcuts import render
from .models import Vente
def liste_ventes(request):
ventes = Vente.objects.filter(ville="Alger").order_by("-date")[:20]
return render(request, "ventes/liste.html", {"ventes": ventes})
# ventes/urls.py
from django.urls import path
from . import views
urlpatterns = [
path("ventes/", views.liste_ventes, name="liste-ventes"),
]
# Commands:
# python manage.py makemigrations && python manage.py migrate
# python manage.py createsuperuser && python manage.py runserver
First project
One model + the admin is enough: expose your data in one hour before coding any page.
Team application
Like Nabil: strict MVT, every database change in a migration, admin as backup back office.
Existing data
Import your CSV into the ORM once (import script), then let Django serve: no more circulating files.
Towards an API
Pure JSON for a separate front end? Keep the Django models and add an API layer (see 4.2) instead of rewriting everything.
✓ Best practices
- Embrace the MVT conventions instead of working around them.
- Migrate from the first model, admin from the first hour.
- Keep SQL basics to optimise the ORM.
✗ Common pitfalls
- Fighting the framework's conventions.
- Writing manual SQL instead of using the ORM.
- Taking Django for a pure, lightweight JSON API.
Key takeaways
- DJANGO = “BATTERIES INCLUDED” framework: admin, ORM, auth, security provided out of the box.
- MVT: MODEL (data) → URL (routing) → VIEW (logic) → TEMPLATE (display).
- ORM = database as Python objects; MIGRATIONS = evolution without manual SQL.
- Auto-generated ADMIN: back office within the first minutes. From CSV analyst to exposed service.
48h challenge — apply tomorrow
Create 1 Django project with 1 model of your own data, migrate, explore the admin and display 1 filtered list in a template.
- I can name MVT, ORM, migrations and admin.
- I know how to create a model and migrate without SQL.
- I have 1 Django page displaying my data.
Frequently asked questions
Django or Flask/FastAPI: how to choose?
Django when you need a complete, structured application: served pages, accounts, permissions, back office — everything is provided and coherent, at the price of embracing its conventions. Flask or FastAPI when you need a lightweight, tailor-made service, typically a JSON API consumed by another client (see 4.2). Nabil remembers: team back office → Django; pure JSON for a front end → API.
Do I need to know SQL to use the Django ORM?
No at first: the ORM is enough to create, read and filter. Yes as soon as it grows: understand tables, indexes and generated queries to optimise slow pages, debug, and write the complex queries the ORM expresses poorly. ORM + SQL basics = the right duo.
Why is Django called “batteries included”?