Skip to content

edx-lms

A statically generated, multi-tenant Learning Management System powered by Next.js 16, consuming content authored in apps/cms.

This page is the documentation entry point. It links to canonical topic pages instead of repeating implementation detail.

Documentation Structure

The docs use four document types. Keep the type clear so readers know whether they are looking at current behavior, implementation history, or proposed work.

Type Purpose Start here
Planning docs Chronological implementation history and design intent by milestone. Milestone 1, Milestone 2, Milestone 3, Milestone 4
Reference docs Current-state implementation details for shipped subsystems or formal proposals. Reference index, Email System, and subsystem pages under reference/
Audience guides Task-oriented instructions for learners, instructors, tenant admins, and operators. Learner Experience, Admin Panel, Deployment, Email Delivery
Developer docs Contributor-facing setup, architecture, and extension guidance for people changing the system. Developer Setup, Database Schema, Authentication

When a shipped feature and future work appear in the same document, keep them in separate Currently implemented and Remaining work sections. Add future work to Roadmap instead of leaving TODOs only in a local reference page.

Root apps/lms/docs/ is the source of truth. The Zensical build (npm run docs:syncdocs:builddocs:publish) syncs these docs and the shared monorepo Cursor rules into docs/zensical/docs-source/ and emits a static site under public/docs/.

How It Works

The documentation pipeline has two sources of truth and one generated output:

  1. Author-owned sources
    • LMS docs under apps/lms/docs/
    • Shared/root platform docs under docs/
    • Cursor rules under .cursor/rules/ and apps/lms/.cursor/rules/
  2. Generated Zensical source
    • npm run docs:sync runs docs/zensical/scripts/sync_docs.py
    • The script mirrors docs into docs/zensical/docs-source/
    • The script also auto-generates the nav = [...] block in docs/zensical/zensical.toml between the auto-generated nav markers
  3. Published static site
    • npm run docs:build renders HTML into docs/zensical/site/
    • npm run docs:publish copies the site into public/docs/ for the app to serve

This means new files (including platform audit tickets under docs/platform-auditing/tickets/) are picked up during sync, and navigation is regenerated automatically from the discovered source tree.

Published Project Rules

The Project Rules navigation publishes every shared rule from the repository .cursor/rules/ directory and every LMS-specific rule from apps/lms/.cursor/rules/. During docs:sync, the sync script strips Cursor frontmatter, rewrites rule links, converts each .mdc source to a .md page, and writes it under docs/zensical/docs-source/rules/. docs:publish copies the built pages into public/docs/, where they are available under /docs/rules/. Do not edit generated docs-source/rules/*.md files.

Canonical References

Use these pages as the source of truth for recurring topics:

Topic Canonical page
Local setup, scripts, tooling Developer Setup And Contributing
Monorepo root scripts/ catalogue Root Scripts Reference
LMS vs CMS dependency drift T-027 CMS vs LMS Drift
Tech stack and shared baselines Tech Stack
Database tables, migrations, dev seed Database Schema
Production database provider decision Production Database ADR
Authentication providers and flows (incl. magic-link + local terminal smoke) Authentication
Email architecture, events, categories, preferences, and persistence state Email System
Email provider setup and troubleshooting Email Delivery
Internationalization i18n
State management and server actions State Management And Hooks
Course → Module → Entry hierarchy Hierarchy Structure
Course enrolment behaviour Course Enrollment System
Per-course flags (course_settings, sequential gating) Course Configuration
Sequential entry pagination + gating Entry Pagination System
Toggleable course sidebar Toggleable Navigation
Quiz authoring + grading wire shape Quiz System
Tenants, feature flags, custom domains Tenant Configuration
API/action error contract (ErrorCode, ActionResult) API and Action Errors
Row-level action menu standards Menu Actions
LMS-owned route OpenAPI (public/openapi.yaml, /admin/api-docs) OpenAPI
Users, roles, RBAC User Management & Access
Super-admin impersonation Impersonation
Dashboards and analytics queries Analytics
Assessment architecture (graded vs formative) Assessment Architecture
Phased build plan Implementation Plan
Admin panel tour Admin Panel
Multi-tenant administration Multi-Tenant Administration
Security headers and rate limits Security And Rate Limiting
Deployment and environment settings Deployment Guide
Learner-facing flows Learner Experience
Course administration Course Administration
Portable Text + widget rendering Content Rendering
Unfinished and proposed work Roadmap
Build-time-only CMS (SSG) transition Roadmap — SSG

Phase Summary

Phase Name Canonical planning page Status
0 Project Foundations Milestone 1 [x]
1 Design System & Layout Shell Milestone 1 [x]
2 Persistence Layer (Kysely + migrations) Milestone 1 [x]
3 Auth.js (v5) Integration Milestone 1 [x]
3.5 Email Provider & Account Flows Milestone 1 [x]
4 Schemas, CMS Client, OpenAPI Milestone 2 [x]
5 Public Website (no auth) Milestone 2 [x]
6 Enrollment Flow Milestone 2 [ ]
7 Entry Pagination & Progress Milestone 2 [ ]
7.5 Assignment Entry Placeholder Milestone 2 [ ]
8 Quiz System Milestone 3 [ ]
9 Dashboards Milestone 3 [ ]
10 Error Handling, Security Headers, Observability Milestone 3 [ ]
10.5 APIs & Well-Known Files Milestone 3 [ ]
11 Testing & CI Milestone 4 [ ]
12 Documentation & Hand-off Milestone 4 [ ]

Milestone 1 status mirrors planning_milestone_1.md. Phases 4+ remain tracked in their milestone docs and roadmap.md.

Open items from these phases are tracked in Roadmap. Creator/marketplace feature proposals (F1–F15) also live in Milestone 4 and the roadmap.

Build Pipeline

Maintainers: project rules and reference markdown are authored under the repo root .cursor/rules/, apps/lms/.cursor/rules/, and apps/lms/docs/. From apps/lms, the pipeline is:

  1. npm run docs:sync (or make -C docs/zensical sync-docs) — runs docs/zensical/scripts/sync_docs.py and writes only into docs/zensical/docs-source/ (Zensical input).
  2. npm run docs:build — runs Zensical and writes static HTML into docs/zensical/site/.
  3. npm run docs:publish — runs docs:build then copies docs/zensical/site/ to public/docs/ for Next.js (predev runs this so local dev serves fresh docs).