Files
phaseflow/specs/cycle-tracking.md
2026-01-10 17:13:18 +00:00

2.7 KiB

Cycle Tracking Specification

Job to Be Done

When I log my period start date, I want the app to calculate my current cycle day and phase, so that training and nutrition guidance is accurate.

Core Concepts

Cycle Day

Day 1 = first day of menstruation.

Calculation:

cycleDay = ((currentDate - lastPeriodDate) mod cycleLength) + 1

Default cycle length: 31 days (configurable per user).

Cycle Phases

Based on a 31-day cycle:

Phase Days Weekly Limit Training Type
MENSTRUAL 1-3 30 min Gentle rebounding only
FOLLICULAR 4-14 120 min Strength + rebounding
OVULATION 15-16 80 min Peak performance
EARLY_LUTEAL 17-24 100 min Moderate training
LATE_LUTEAL 25-31 50 min Gentle rebounding ONLY

API Endpoints

POST /api/cycle/period

Log a new period start date.

Request Body:

{
  "startDate": "2024-01-10"
}

Behavior:

  1. Update user.lastPeriodDate
  2. Create PeriodLog record for history
  3. Recalculate today's cycle day and phase

GET /api/cycle/current

Returns current cycle information.

Response:

{
  "cycleDay": 12,
  "phase": "FOLLICULAR",
  "daysUntilNextPhase": 3,
  "phaseConfig": {
    "weeklyLimit": 120,
    "dailyAvg": 17,
    "trainingType": "Strength + rebounding"
  }
}

Cycle Utilities (src/lib/cycle.ts)

Functions:

  • getCycleDay(lastPeriodDate, cycleLength, currentDate) - Calculate day in cycle
  • getPhase(cycleDay) - Determine current phase
  • getPhaseConfig(phase) - Get phase configuration
  • getPhaseLimit(phase) - Get weekly intensity limit

Constants:

  • PHASE_CONFIGS - Array of phase definitions

Period History

PeriodLog Schema

interface PeriodLog {
  id: string;
  user: string;
  startDate: Date;
  created: Date;
}

History Display (/history)

  • List of all logged period dates
  • Calculated cycle lengths between periods
  • Average cycle length over time
  • Ability to edit/delete entries

Configurable Cycle Length

Users with irregular cycles can adjust:

  • Default: 31 days
  • Range: 21-45 days
  • Affects phase day boundaries proportionally

Success Criteria

  1. Cycle day resets to 1 on period log
  2. Phase transitions at correct day boundaries
  3. Weekly limits adjust per phase automatically
  4. History shows all logged periods

Acceptance Tests

  • getCycleDay returns 1 on period start date
  • getCycleDay handles cycle rollover correctly
  • getPhase returns correct phase for each day range
  • POST /api/cycle/period updates user record
  • GET /api/cycle/current returns accurate phase info
  • Days beyond cycle length default to LATE_LUTEAL