Files
pragativeer-v2/backend/worker.py

85 lines
3.1 KiB
Python

import os
from datetime import datetime, timedelta
from celery import Celery
from celery.schedules import crontab
from sqlmodel import Session, select
import json
from database import engine
import models
REDIS_URL = os.getenv("REDIS_URL", "redis://redis:6379/0")
# Initialize Celery connected to our local Redis broker
celery_app = Celery(
"pragativeer_tasks",
broker=REDIS_URL,
backend=REDIS_URL
)
# Configure timezone to IST for accurate 5:00 AM scheduling
celery_app.conf.update(
timezone='Asia/Kolkata',
enable_utc=True,
)
@celery_app.task(name="generate_daily_study_plans", bind=True, default_retry_delay=60, max_retries=3)
def generate_daily_study_plans(self):
"""
Runs daily to evaluate students' weak areas and generate
a personalized AI study plan for the day.
"""
try:
with Session(engine) as session:
# Fetch all active users on the AI Coach tier
ai_students = session.exec(
select(models.User).where(models.User.tier == models.TierEnum.AI_COACH)
).all()
today = datetime.utcnow().date()
plans_created = 0
for student in ai_students:
# 1. Fetch pending spaced repetition mistakes for today
pending_mistakes = session.exec(
select(models.Mistake)
.where(models.Mistake.user_id == student.id)
.where(models.Mistake.is_mastered == False)
.where(models.Mistake.next_review <= datetime.utcnow())
).all()
# 2. Extract weak topics (for revision recommendation)
topics = [m.topic for m in pending_mistakes]
most_weak_topic = max(set(topics), key=topics.count) if topics else "Mixed Syllabus"
# 3. Construct the time-budgeted dynamic task list
tasks = [
{"type": "Revision", "description": f"Revise {most_weak_topic}", "duration_minutes": 15, "status": "Pending"},
{"type": "Mistake_Review", "description": "Daily Mistake Review Session", "duration_minutes": 10, "status": "Pending"},
{"type": "DPS", "description": f"Attempt {most_weak_topic} Practice Sheet", "duration_minutes": 20, "status": "Pending"}
]
# 4. Save to Database
new_plan = models.StudyPlan(
user_id=student.id,
date=today,
tasks=tasks,
is_completed=False
)
session.add(new_plan)
plans_created += 1
session.commit()
return f"Successfully generated {plans_created} daily study plans."
except Exception as exc:
print(f"Database error during study plan generation: {exc}")
raise self.retry(exc=exc)
# Schedule the tasks using Celery Beat
celery_app.conf.beat_schedule = {
'generate-study-plans-every-morning': {
'task': 'generate_daily_study_plans',
'schedule': crontab(hour=5, minute=0), # 5:00 AM IST
},
}