Django Celery Integration incorporates the Celery distributed task queue into a Django application to offload time-consuming, synchronous tasks to asynchronous background worker processes.
If a user uploads a video, processing that video takes 5 minutes. If Django does this in the view, the user’s browser spins for 5 minutes waiting for a response. Celery allows the view to instantly say “Video received!”, and hands the actual processing task to a separate worker program in the background.
- A message broker (like Redis or RabbitMQ) is set up.
- A task is defined in Django using the
@shared_taskdecorator. - The view calls
task_name.delay(args). - Django pushes a message onto the broker queue.
- A separate Celery worker process (running independently of the web server) picks up the message from the queue and executes the Python function.
graph LR A[Django View] -->|task.delay()| B(Message Broker: Redis) B --> C(Celery Worker Process) C --> D[(Database)] A --> E[Immediate HTTP Response]
Celery is like a restaurant kitchen. The waiter (Django View) takes the order and gives it to the kitchen counter (Message Broker), and immediately returns to the customer (HTTP Response). The chefs in the back (Celery Workers) pick up the orders and do the heavy lifting of cooking the food asynchronously.
from celery import shared_task
@shared_task
def send_bulk_emails():
# Long running process
pass
# In views.py
def register_user(request):
# trigger async task
send_bulk_emails.delay()
return HttpResponse("Registered!")- Requires a Message Broker (Redis/RabbitMQ).
- Tasks run in isolated processes, separate from the WSGI server.
- Prevents HTTP timeouts for long-running operations.
- Built from: Python — Celery is a Python task queue.
- Related: Django View — views trigger celery tasks.
- Contrasts with: Django Signals — signals are synchronous, Celery is asynchronous.
- Passing Django ORM objects (like a user instance) to a Celery task is dangerous because the object might change in the DB before the task runs. Always pass the primary key (
user_id) instead, and let the task fetch the fresh object from the DB.