From 71b3bca058a4bee27a6a96e0f5da4fb4d544aa1f Mon Sep 17 00:00:00 2001 From: Omid Hashemzadeh Date: Wed, 14 May 2025 16:06:55 +0100 Subject: [PATCH 1/2] add celery to docker-compose --- README.md | 31 ++++++++++++++++++++++++++----- docker-compose.yml | 13 ++++++++++++- tasks/tasks.py | 2 +- 3 files changed, 39 insertions(+), 7 deletions(-) diff --git a/README.md b/README.md index db6d808..fa5b03b 100644 --- a/README.md +++ b/README.md @@ -9,7 +9,8 @@ A Django RESTful API for managing personal or team tasks — featuring PostgreSQ - ✅ Django 5 + Django REST Framework - ✅ PostgreSQL database (via Docker) -- ✅ RabbitMQ for background tasks (Celery-ready) +- ✅ RabbitMQ for background tasks (Celery integrated) +- ✅ Asynchronous task logging using Celery - ✅ Environment config with `.env` and `python-decouple` - ✅ Swagger UI for API documentation - ✅ Containerized with Docker @@ -21,12 +22,13 @@ A Django RESTful API for managing personal or team tasks — featuring PostgreSQ ``` taskflow-api/ -├── taskflow_api/ # Django project -├── tasks/ # App: task models, views, serializers +├── taskflow_api/ # Django project (includes celery.py) +├── tasks/ # App: task models, views, serializers, signals, celery tasks ├── requirements.txt # Python dependencies ├── Dockerfile # Production image for gunicorn ├── docker-compose.yml # DB and RabbitMQ container setup ├── .env # Environment configuration +├── logs/ # Directory for activity logs (auto-created) ├── run_server.sh # Run production server (Gunicorn) └── start-dev-services.sh # Run DB + RabbitMQ for development ``` @@ -79,7 +81,7 @@ Use this when you want to run Django locally (`runserver`) and containers only f > This will: > - Start PostgreSQL and RabbitMQ containers -> - Stop and remove any running `web` container +> - Stop and remove any running web container > - Run DB migrations automatically ### ▶️ Then Run Django: @@ -87,12 +89,30 @@ Use this when you want to run Django locally (`runserver`) and containers only f python3 manage.py runserver ``` +### ▶️ Run Celery Worker: +```bash +celery -A taskflow_api worker --loglevel=info +``` + Open: - Swagger docs: http://localhost:8000/docs/ - API root: http://localhost:8000/api/tasks/ --- +## 🧩 Celery Logging Task + +When a task is created through the API, a Celery worker will automatically: + +- Run `log_task_action` in the background using `celery -A taskflow_api worker --loglevel=info` +- Write an entry like this to `logs/task_activity.log`: + +``` +[2025-09-14 19:45:00] Task #12 ('Example Task') was created +``` + +--- + ## 🏭 Production Mode (Dockerized Web) ### ▶️ Build & Run All Services: @@ -117,6 +137,7 @@ docker compose up --build - **Backend**: Django 5, DRF - **Database**: PostgreSQL (Docker) - **Broker**: RabbitMQ (Docker) +- **Background Jobs**: Celery (activity logging) - **Containerization**: Docker, Docker Compose - **CI-ready**: Gunicorn + environment-based config @@ -124,4 +145,4 @@ docker compose up --build ## 📜 License -MIT © Omid Hashemzadeh +MIT © Omid Hashemzadeh \ No newline at end of file diff --git a/docker-compose.yml b/docker-compose.yml index f85b228..f9c5b15 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -26,4 +26,15 @@ services: image: rabbitmq:management ports: - "5672:5672" - - "15672:15672" \ No newline at end of file + - "15672:15672" + + celery: + build: . + command: celery -A taskflow_api worker --loglevel=info + volumes: + - .:/app + depends_on: + - db + - rabbitmq + env_file: + - .env diff --git a/tasks/tasks.py b/tasks/tasks.py index 4974001..fb2fd99 100644 --- a/tasks/tasks.py +++ b/tasks/tasks.py @@ -8,7 +8,7 @@ def log_task_action(task_id, action): """Log task ID and title to a file.""" try: task = Task.objects.get(id=task_id) - log_line = f"[{now()}] Logging Celery Task : Task #{task.id} ('{task.title}') was {action} using celery.\n" + log_line = f"[{now()}] Task #{task.id} ('{task.title}') was {action} via Celery background task.\n" except Task.DoesNotExist: log_line = f"[{now()}] ERROR: Task {task_id} not found for action '{action}'\n" From 0582894b27b377482e046c385d2e9014c8cddb86 Mon Sep 17 00:00:00 2001 From: Omid Hashemzadeh Date: Wed, 14 May 2025 16:33:28 +0100 Subject: [PATCH 2/2] fix: docker-compose environment variable override for CELERY_BROKER_URL --- README.md | 2 +- docker-compose.yml | 11 +++++++++-- lint-clean.sh | 11 +++++++++++ 3 files changed, 21 insertions(+), 3 deletions(-) create mode 100755 lint-clean.sh diff --git a/README.md b/README.md index fa5b03b..8eac8f0 100644 --- a/README.md +++ b/README.md @@ -108,7 +108,7 @@ When a task is created through the API, a Celery worker will automatically: - Write an entry like this to `logs/task_activity.log`: ``` -[2025-09-14 19:45:00] Task #12 ('Example Task') was created +[2025-09-14 19:45:00] Task #12 ('Example Task') was created via Celery background task. ``` --- diff --git a/docker-compose.yml b/docker-compose.yml index f9c5b15..6f2abda 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -12,7 +12,10 @@ services: env_file: - .env environment: + # Useful if override needed, else .env handles it POSTGRES_HOST: db + CELERY_BROKER_URL: amqp://guest:guest@rabbitmq:5672// + db: image: postgres @@ -25,8 +28,8 @@ services: rabbitmq: image: rabbitmq:management ports: - - "5672:5672" - - "15672:15672" + - "5672:5672" # AMQP (used by Celery) + - "15672:15672" # RabbitMQ management UI celery: build: . @@ -38,3 +41,7 @@ services: - rabbitmq env_file: - .env + environment: + # Useful if override needed, else .env handles it + POSTGRES_HOST: db + CELERY_BROKER_URL: amqp://guest:guest@rabbitmq:5672// diff --git a/lint-clean.sh b/lint-clean.sh new file mode 100755 index 0000000..e074be9 --- /dev/null +++ b/lint-clean.sh @@ -0,0 +1,11 @@ +#!/bin/bash + +echo "🔍 Linting and fixing with Ruff (ignoring migrations)..." + +# Lint and auto-fix, ignoring migration files +ruff check --fix . --exclude migrations + +# Format code (also ignores excluded by default) +ruff format . --exclude migrations + +echo "✅ Code linted and formatted!"