docs(phase6a): document RootNode course foundation

COURSE_AUTHORING_STANDARD.md — the standard every future lesson/module
must follow (target learner, prerequisites, measurable objectives,
concept-before-lab, instructor notes, terminology, versioning, review
requirements), grounded in the gold-standard module as the reference
implementation.

PHASE6A_ROOT_COURSE_FOUNDATION.md — the phase summary: youth-ladder
context, the Google Workspace status already recorded in Phase 5C's own
docs, architecture/build summary, honest content states, test results,
explicit non-goals, and known limitations/Phase 6B recommendations.

Updated ENGINEERING_SOP.md (new Phase 6A section + a curriculum-content
cross-reference), REMOTE_AND_SELF_PACED_ARCHITECTURE.md (a 7th
closed gap: self-paced enrollment now resolves to a real course tree,
not just a scenario list), LAB_ARCHITECTURE.md (Phase 6A reuses the
disposable Lab unmodified, verified by a real rehearsal), and
platform/README.md (course model in the api/ summary, new e2e suite
descriptions for 5A/5B/5C/6A which were missing entirely, and the
real-Lab rehearsal script).

Co-Authored-By: Claude Sonnet 5 <[email protected]>
This commit is contained in:
2026-08-25 23:30:11 -05:00
co-authored by Claude Sonnet 5
parent 8ffc923a84
commit fd38d06055
6 changed files with 350 additions and 8 deletions
+45 -3
View File
@@ -88,6 +88,12 @@ To add/reorder a stage: edit `rootnode-path.json` directly, referencing existing
`scenarios/data/*.json` ids. No backend code change needed — it's read fresh via
`POST /api/cache/reload` or on server restart.
As of Phase 6A, `root_` also has a course/module/activity layer ON TOP of this (lessons,
demonstrations, guided exercises around the same scenario ids) — see §17 and
`docs/COURSE_CONTENT_MODEL.md`. `rootnode-path.json` itself is unmodified and still the thing
`curriculum-rules.js` computes stage lock/completion from; the course layer is a parallel,
additive structure that references the same scenario ids, not a replacement.
## 5. Student identity — what's built, what isn't
**Current state (Phase 5A — see `docs/PHASE5A_STUDENT_IDENTITY_REMOTE_CLASSROOM.md` for the
@@ -416,6 +422,42 @@ Full design: `docs/PHASE5C_ENROLLMENT_COMMUNICATIONS.md`, plus
from website enrollment through a real rendered/extracted activation email, a real Lab launch
and scenario completion, a second enrollment's confirmation email, and a full password-reset
round trip) — both against a live stack, using only the dev provider (no real network calls).
Live Google Workspace delivery itself is implemented and unit-level ready
(`infra/scripts/gws-email-test.js`, opt-in) but not yet validated against a real Workspace
domain — see that doc's final section.
Live Google Workspace delivery has since been validated for real, end to end, via
`academy@rootnodeacademy.com` — see `docs/PHASE5C_ENROLLMENT_COMMUNICATIONS.md` §14.
## 17. ROOT_ Course Architecture + Content Delivery Foundation (Phase 6A)
Full design: `docs/PHASE6A_ROOT_COURSE_FOUNDATION.md`, plus `docs/ROOT_CURRICULUM_INVENTORY.md`,
`docs/ROOT_PROGRAM_ARCHITECTURE.md`, `docs/COURSE_CONTENT_MODEL.md`, and
`docs/COURSE_AUTHORING_STANDARD.md`.
- **What it is:** a course → module → activity content model (`022_course_content.sql`) layered
over the existing scenario/assessment/achievement systems for `root_` only, so a lesson can be
taught BEFORE a lab is presented instead of the platform only ever showing a bare scenario
list. A `lab` activity references an existing `scenario_id`; an `assessment`/`capstone`
activity references an existing `assessment_definition_id` — neither duplicates content.
Long-form lesson prose lives in git-tracked Markdown (`content/root/`), split into
shared/instructor-only sections by a `## Instructor Notes` heading convention
(`content.js`). One `buildCourseTree()` (`course-progress.js`) serves both the self-paced
student route and the instructor curriculum view — no forked curriculum for the two delivery
modes.
- **Completion, never a second source of truth:** a lab's completion reads the existing
`progress` table; an assessment/capstone activity's completion reads the existing
`achievements` table; only lesson-only activities (nothing else to derive completion from) get
the one genuinely new table, `activity_completions`.
- **A real bug found and fixed during testing:** computing a module/course's prerequisite lock
and then stripping its working totals in the SAME map iteration made the result depend on Map
iteration order — a dependent entry could see its prerequisite's totals already deleted. Fixed
by splitting into two explicit passes (`course-progress.js`).
- **One gold-standard module fully authored:** ROOT 10's Kubernetes Health Probes &
Troubleshooting (lesson → demonstration → knowledge check → guided exercise → real Lab
`rootnode-probe-port-mismatch` → reflection), the template `docs/COURSE_AUTHORING_STANDARD.md`
documents for all future modules. Every other course is honestly `partial` (real labs, no
lessons yet) or `planned` (no content exists) — nothing was fabricated to look finished.
- **Tested, not just designed:** `platform/test/e2e-phase6a.js` (21 checks: hierarchy/ordering,
all three completion behaviors, prerequisite locking, resume, cross-student isolation, RBAC
for self-paced no-cohort students, draft-content hiding, version stability) and
`infra/scripts/drills/test-phase6a-course-rehearsal.js` (12 checks, real k3s: a student reads
the gold module's real lesson content, launches a real Lab, the Lab's own `setup_commands`
stand up the broken deployment, a real `kubectl patch` fixes it, and the module completes and
unlocks the next one) — both against a live stack.