LLM-Powered Personalized Scheduling System for Students
FrameTime uses Large Language Models to automatically generate personalized timetables by analyzing your activities, deadlines, and preferences in natural language.
- Natural Language Input: Describe your schedule in plain English
- Intelligent Scheduling: Hybrid approach combining algorithmic scheduling for fixed activities and LLM-powered optimization for variable tasks
- Iterative Refinement: Automatic schedule improvement through AI-powered feedback and optimization
- User Profile Integration: Respects your sleep schedule, work style, and preferences
- Multiple Interfaces: Web interface (default) or command-line interface
- Google Calendar Export: Export schedules directly to Google Calendar (optional)
# Clone and navigate to the project
cd FrameTime
# Create a virtual environment (recommended)
python -m venv venv
# Activate the virtual environment
# On Windows:
venv\Scripts\activate
# On macOS/Linux:
source venv/bin/activate
# Install dependencies
pip install -r requirements.txt
# Create .env file in project root and add:
cp .env.example .env
# Configure your OpenAI API key
OPENAI_API_KEY=your_api_key_hereFrameTime supports exporting your generated schedule directly to Google Calendar.
-
Create Google Cloud OAuth Credentials
- Go to Google Cloud Console
- Create OAuth client ID (Desktop App type)
- Download JSON and rename to
credentials.json - Place in project root directory
-
Enable Google Calendar API
- Go to Calendar API page
- Click Enable
-
Add Test User
- Go to OAuth consent screen
- Add your email as a test user
-
Configure Environment
- Add to
.envfile:GOOGLE_CALENDAR_SCOPES=https://www.googleapis.com/auth/calendar GOOGLE_CALENDAR_CREDENTIALS_PATH=credentials.json
- Add to
-
Usage
- The system will automatically look for a calendar named
frametime - If it doesn't exist, it will create one
- All scheduled blocks are inserted as events
- The system will automatically look for a calendar named
Web Interface (Recommended - Default Mode)
python main.pyThis launches a web interface at http://127.0.0.1:7860 where you can:
- Enter scheduling information in natural language
- Review structured input parsing
- Generate optimized schedules
- View results interactively
CLI Mode with Input Files
python main.py --cli --input test_1This loads three files with the same base name:
data/input/scheduling_periods/test_1.txtdata/input/activities/test_1.txtdata/input/user_profiles/test_1.txt
FrameTime uses three separate text files for input (CLI mode), all sharing the same base name.
Specify the time period for scheduling:
I need help scheduling my week from November 15 to November 27, 2025.
List your fixed activities and deadlines:
I have the following fixed activities:
- ECE1724 lecture every Thursday from 6:10pm to 9:10pm
- MIE1628 class on Friday from 5pm to 8pm
- ECE1786 lecture every Tuesday from 9:10am to 11:10am
- Gym session twice a week on Monday and Wednesday from 6pm to 7:30pm
- Badminton once a week on Saturday from 7pm to 9pm
I also have these deadlines coming up:
- ECE1724 assignment due on November 19 at 9pm (will take about 6 hours)
- Prepare for MIE1628 exam on November 25 at 6pm (need 10 hours of study time)
- Read research paper for seminar on November 18 (about 3 hours)
Describe your preferences and lifestyle:
About my preferences:
- I wake up at 8:30am and go to sleep at 1am
- I have a consistent daily routine
- I prefer to work proactively and get things done ahead of time rather than cramming
- I like to maintain a balanced lifestyle between work and personal time
- My stress level is low
Scheduling Period:
- Start and end dates for your schedule
Activities:
- Fixed Activities: Classes, appointments, recurring events with specific times
- Variable Activities: Assignments, projects, exams with due dates and estimated workload
User Profile:
- Wake up and sleep times
- Routine consistency (consistent/variable)
- Pacing style (proactive/crammer)
- Work-life balance preference (work_focus/balanced/life_focus)
- Stress level (low/medium/high)
- Schedule type (weekdays/weekends/all_days)
FrameTime uses a hybrid scheduling approach:
-
Input Processing: Natural language → Structured JSON (InputProcessingAgent)
- Parses your text input into structured data
- Extracts fixed activities, variable activities, and user profile
-
Fixed Activity Scheduling: Algorithm-based deterministic scheduling
- Handles recurring patterns (daily, weekly, custom)
- Calculates all occurrences within the scheduling period
-
Variable Activity Scheduling: LLM-powered optimization
- Schedules variable tasks in available time slots
- Applies user profile filtering (sleep schedule, study hours, preferences)
- Respects deadlines and priorities
-
Iterative Refinement: Three-tier AI-powered schedule improvement
- Tier 1 (Initial Generation): LLM creates initial schedule from scratch
- Tier 2 (Fix Hard Constraints): If hard constraints fail, LLM fixes violations while preserving activities
- Tier 3 (Optimize Soft Constraints): If hard constraints pass, LLM optimizes user preference alignment
- CriticAgent evaluates schedule quality (0-100 score) after each iteration
- Continues until score threshold is met or max iterations reached
-
Output: Final schedule saved as JSON and optionally exported to Google Calendar
All modes save the following files:
-
Processed Input:
data/output/processed_inputs/processed_input_{timestamp}.json- Structured data parsed from your natural language input
-
Draft Schedules:
data/output/draft_schedules/draft_iter{N}_{timestamp}.json- Each iteration's schedule during refinement process
-
Final Schedule:
data/output/final_schedules/final_schedule_{timestamp}.json- The approved schedule in JSON format with time blocks
-
User Feedback:
data/output/user_feedback/user_feedback.jsonl- User feedback collected from the web interface
- Stored in JSONL format (one JSON object per line)
- Contains ratings for personalization, practicality, and effectiveness, plus optional comments
-
Google Calendar Export: Events exported directly to Google Calendar
- All scheduled time blocks are automatically exported to your Google Calendar
- Events are created in a calendar named
frametime(created automatically if it doesn't exist) - Requires Google Calendar API setup (see Google Calendar Export Setup section)
Each schedule contains:
schedule: List of time blocks with:activity_name: Name of the activityactivity_type: Type (work, course, exercise, etc.)start_time: Start time inYYYY-MM-DD HH:MMformatend_time: End time inYYYY-MM-DD HH:MMformatnotes: Explanation of scheduling decisionrelated_flexible_activity: Related variable activity name (if applicable)
reasoning: AI explanation of scheduling strategypotential_issues: List of concerns or trade-offs
python main.py [OPTIONS]- (default) Web interface mode - Interactive browser-based UI
--cliEnable CLI mode (requires--input)
--input NAME, -i NAMEBase name for input files (e.g., "test_1")
--port PORTPort for web interface (default: 7860)
--verbose, -vEnable verbose logging (DEBUG level)--quiet, -qQuiet mode (WARNING level only)
# Launch web interface (default)
python main.py
# Web interface on custom port
python main.py --port 8080
# CLI mode with input files
python main.py --cli --input test_1provider: "openai"
model: "gpt-5.1"
temperature: 0.7 # Default temperature for GPT-5.1 when reasoning_effort="none"
max_output_tokens: 10000
reasoning_effort: "low" # Options: "none", "low", "medium", "high" (temperature only works with "none")
text_verbosity: "medium" # Options: "low", "medium", "high"manager:
max_iterations: 5 # Maximum refinement iterations
score_threshold: 85.0 # Acceptance score threshold
scheduling:
min_break_duration_minutes: 15
max_continuous_work_hours: 3
default_work_chunk_hours: 2
buffer_before_deadline_hours: 2
critic:
min_acceptable_score: 70.0
weight_constraint_satisfaction: 0.4
weight_user_preferences: 0.3
weight_workload_balance: 0.3FrameTime/
├── main.py # Main entry point
├── src/
│ ├── app/ # Application layer
│ │ ├── frame_time.py # Backend orchestration
│ │ ├── gradio.py # Web interface frontend
│ │ └── google_calendar_export.py # Calendar export
│ ├── core/ # Core services
│ │ ├── config_manager.py # Configuration management
│ │ ├── llm_service.py # LLM API wrapper
│ │ ├── prompt_manager.py # Prompt templates
│ │ └── lifestyle_benchmark.py # Lifestyle analysis
│ ├── agents/ # Agent implementations
│ │ ├── base_agent.py # Base agent class
│ │ ├── input_processing_agent.py # Parses natural language
│ │ ├── scheduling_agent.py # Generates schedules
│ │ └── critic_agent.py # Evaluates schedule quality
│ └── models/ # Data models (Pydantic)
│ ├── activity.py # Activity models
│ ├── schedule.py # Schedule models
│ ├── feedback.py # Critic feedback models
│ ├── user_profile.py # User profile models
│ └── scheduling_period.py # Period models
├── config/
│ ├── llm_config.yaml # LLM settings
│ ├── app_config.yaml # System parameters
│ └── prompts/ # LLM prompt templates
│ ├── input_processing.txt
│ ├── edited_input_processing.txt
│ ├── scheduling.txt
│ ├── scheduling_fix_hard_constraints.txt
│ ├── scheduling_optimize_soft_constraints.txt
│ └── critic.txt
├── data/
│ ├── input/ # Input files
│ │ ├── scheduling_periods/
│ │ ├── activities/
│ │ └── user_profiles/
│ ├── output/ # Generated schedules
│ │ ├── processed_inputs/
│ │ ├── draft_schedules/
│ │ ├── final_schedules/
│ │ └── user_feedback/
│ └── course_db/ # Course database
├── .env # API keys (create from .env.example)
├── requirements.txt # Python dependencies
└── README.md # This file
- Ensure
.envfile exists in project root - Check that
OPENAI_API_KEYis set correctly - Restart the application after setting the API key
- Use a different port:
python main.py --port 8080 - Or stop the process using port 7860
- Make sure all three files exist with the same base name:
data/input/scheduling_periods/{name}.txtdata/input/activities/{name}.txtdata/input/user_profiles/{name}.txt
- Note: Web interface doesn't require input files
- Check internet connection
- Verify OpenAI API key is valid
- Check API credits at platform.openai.com
- The service includes automatic retry logic
- Adjust
score_thresholdinconfig/app_config.yaml - Increase
max_iterationsfor more refinement attempts - Make sure your constraints are realistic
- Provide more detailed information in your input
- Check that the server started successfully
- Verify the port is accessible:
http://127.0.0.1:7860 - Check firewall settings if accessing from another machine
- Input Processing: Natural language → Structured JSON (InputProcessingAgent)
- Fixed Activity Scheduling: Algorithm schedules all fixed activities deterministically
- Available Slot Calculation: System calculates gaps between fixed activities
- Variable Activity Scheduling: LLM schedules variable tasks in available slots with user profile filtering
- Evaluation: CriticAgent evaluates schedule quality and provides feedback
- Iteration (Three-Tier Strategy):
- Tier 1: Initial schedule generation from scratch
- Tier 2: Fix hard constraint violations (if any)
- Tier 3: Optimize soft constraints for user preferences (if hard constraints pass)
- Continues until score threshold is met or max iterations reached
- Output: Final schedule saved and optionally exported
- FrameTimeApp: Main orchestration class
- InputProcessingAgent: Parses natural language input
- SchedulingAgent: Hybrid scheduling (algorithm + LLM)
- CriticAgent: Evaluates and provides feedback on schedules
- GradioApp: Web interface frontend
This project is part of a course assignment for ECE1786 NLP.