Files
learning-platform/docs/curriculum-spec.md
RaymondVerhoef 07af2783dc
All checks were successful
On Push to Main / test (push) Successful in 1m33s
On Push to Main / publish (push) Successful in 1m31s
On Push to Main / deploy-dev (push) Successful in 2m3s
Add comprehensive documentation for key organizational aspects
- Introduced "Pension Scheme & Benefits" detailing secondary employment benefits and pension specifics.
- Created "Roles & Accountabilities" outlining the Holacracy role structure and responsibilities within Respellion.
- Added "Security" section covering GDPR compliance and workplace safety protocols.
- Established "Spending and Contracting" policy detailing expense categories and submission processes.
- Documented "Who We Are" to define Respellion's identity, services, and operational model under Holacracy and ISO 9001.
2026-05-27 08:24:56 +02:00

3.5 KiB
Raw Permalink Blame History

Curriculum spec: 26-week per-user cycle

The curriculum sequences the knowledge base into a 26-week schedule. Every employee runs their own cycle, starting when they enroll. Implemented in src/lib/curriculumService.js; admin UI in src/components/admin/CurriculumManager.jsx.


Data

  • curriculum_versions — generated schedules. Lifecycle draft → active → superseded; exactly one active. The schedule JSON is an array of 26 week objects: { week_number (126), theme, topic_ids[], estimated_duration (1545), week_rationale }. coverage_stats records theme/topic coverage.
  • topics — supply theme, complexity_weight (15), and difficulty as generation input.

Topic enrichment (prerequisite)

Generation needs themed, weighted topics. enrichTopicsForCurriculum() finds topics missing a theme (excluding type='fact' and learning_relevance='exclude') and, in batches of 20, calls Claude with emit_topic_enrichment to assign theme, complexity_weight, and difficulty. Triggered from the Curriculum tab.


Generation

generateCurriculumDraft(reason):

  1. Group learning topics by theme (buildThemeTopicMap), sorted by complexity_weight ascending.
  2. Build a prompt describing themes and their topic ids. If there are more than 26 themes, the model is instructed to merge closely related themes.
  3. callLLM (standard tier, maxTokens: 8192, temp 0) with forced emit_curriculum_schedule. Up to 2 attempts; on validation failure the errors are fed back into the retry prompt.
  4. Validate (validateSchedule): exactly 26 weeks, correct week_number sequence, durations 1545, every topic_id exists, ≥1 topic per week. Unscheduled themes are warnings, not hard errors.
  5. Supersede any existing draft and store the new draft version with coverage stats.

confirmVersion(versionId, adminUserId) activates a draft (and supersedes the old active version); rejectVersion discards a draft.


Per-user scheduling (the cycle)

The cycle is detached from the calendar. Enrollment sets team_members.curriculum_started_at (see docs/frontend-spec.md for onboarding). AppContext derives the user's position:

getPersonalWeekNumber(startedAt)  // floor(daysSinceStart / 7) + 1, ≥1 (0 if not enrolled)
getCurriculumWeek(personalWeek)   // ((n - 1) % 26) + 1    → 1..26 slot
getCurriculumCycle(personalWeek)  // floor((n - 1) / 26) + 1 → 1, 2, 3, ...
  • Week 1 begins the day the employee enrolls.
  • After week 26 the cycle restarts at week 1 with the same content.
  • state.weekNumber (the absolute counter) is 0 until the user enrolls; pages are gated behind onboarding so they never render with week 0.

Content & progress for a week

  • getCurrentWeekContent(personalWeek) reads the active version's schedule, maps the 26-week slot to its topic_ids, and returns { cycle, weekNumber, theme, topics, estimatedDuration, rationale }.
  • getAssignedTopic(userId, week) returns the week's primary topic, falling back to a deterministic hash of userId:week when no curriculum is active. Keep the fallback.
  • getYearProgress(userId, personalWeek) computes completion for the current cycle.

Notes

  • There is no shared "current week" and no admin:current_week setting.
  • Regeneration produces a new version; activating it changes future weeks for all users. Completion history (micro_learning_completions) is append-only and never rewritten.