Skip to content

Add client-side RBAC with course ownership and content locking - #1102

Open
lgriffin wants to merge 4 commits into
tutors-sdk:developmentfrom
lgriffin:feat/rbac-content-locking
Open

Add client-side RBAC with course ownership and content locking#1102
lgriffin wants to merge 4 commits into
tutors-sdk:developmentfrom
lgriffin:feat/rbac-content-locking

Conversation

@lgriffin

@lgriffin lgriffin commented Jul 23, 2026

Copy link
Copy Markdown
Contributor

Summary

Introduces a client-side role-based access control (RBAC) system enabling lecturers to manage course content visibility at runtime. This is a foundational step toward giving course owners control over student progression — locking/unlocking topics, units, and individual learning objects, and gating capabilities like quizzes.

How it works

  • Course ownership: Course authors set owner: github-login and/or lecturers: login1,login2 in their course properties.yaml. On load, the app compares these against the authenticated user's GitHub login to determine lecturer status.
  • Content locking: Lecturers can toggle locks on cards and units via inline buttons or the Lecturer Panel sidebar. Students see locked content as greyed-out cards with a lock icon overlay — visible but not navigable. Direct URL navigation to locked content redirects to the course page.
  • Lock persistence: Lock state is stored in a Supabase table (tutors_content_locks) with a localStorage fallback, so it works locally without Supabase and degrades gracefully.
  • Lecturer Panel: A new sidebar accessible from the nav bar (visible only to lecturers) with three tabs:
    • Locks — tree of all lockable content with toggle controls
    • Enrollment — read-only view of the course whitelist and student list
    • Access — surfaces existing learning records and activity data

Key design decisions

  • Purely client-side: All role checks and lock enforcement happen in the browser. This is consistent with the existing access control model (authLevel, whitelist, isPrivate are all client-side today). No server-side API routes or Supabase RLS.
  • localStorage fallback: The RBAC service stores lock state in localStorage when Supabase is unavailable, enabling local development and testing without any backend setup.
  • Dev mode auto-lecturer: When running npm run dev and no owner/lecturers is configured, a dev lecturer identity is auto-created. Press L to toggle between lecturer and student views for testing.

New files

  • src/lib/services/rbac/ — types, lock management service, re-exports
  • src/lib/ui/navigators/buttons/LecturerButton.svelte — nav bar sidebar trigger
  • src/lib/ui/learning-objects/content/LecturerPanel.svelte — sidebar panel with locks/enrollment/analytics

Modified files

  • runes.svelte.tsisLecturer, courseLecturers, contentLocks runes
  • lo-tree.ts — lecturer extraction from course properties
  • (course-reader)/+layout.svelte — lecturer computation, lock loading, route guard
  • supabase-client.ts — lock CRUD and learning records query
  • Cards.svelte, Units.svelte — lock overlay and toggle UI
  • MainNavigator.svelte — conditional LecturerButton
  • All 4 icon theme files — lock/unlock/lecturer icons
  • keyboard-shortcuts.ts, en.ts, TutorsShell.svelte — L shortcut for dev view toggle

Supabase table required

CREATE TABLE tutors_content_locks (
  course_id TEXT NOT NULL,
  lo_route TEXT NOT NULL,
  locked BOOLEAN NOT NULL DEFAULT true,
  locked_by TEXT NOT NULL,
  locked_at TIMESTAMPTZ NOT NULL DEFAULT now(),
  PRIMARY KEY (course_id, lo_route)
);

The feature degrades gracefully without this table (uses localStorage only).

Test plan

  • Set owner: your-github-login in a test course's properties.yaml
  • Log in with matching GitHub account — LecturerButton appears in nav
  • Toggle locks on cards via inline toggle or Lecturer Panel
  • Verify locked cards appear greyed out with lock icon for students
  • Verify direct URL navigation to locked LOs redirects to course page
  • Verify locks persist across page refresh (localStorage)
  • Dev mode: press L to toggle lecturer/student view
  • Verify no build errors introduced

🤖 Generated with Claude Code

Related

Tracks production hardening in #1103

lgriffin and others added 4 commits July 22, 2026 14:45
Press ? on any page to see a context-aware keyboard shortcuts
reference. Shows general shortcuts plus section-specific ones
for labs (arrow key step nav), presentations (slide nav), and
notebooks (cell nav). Uses native <dialog> with showModal() for
proper focus trapping and backdrop. Arrow keys are suppressed
in content components while the overlay is open.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Press F to hide the navigation bar and footer for distraction-free
reading. Press F again to restore them. Uses the existing
hideMainNavigator rune. Added to the keyboard shortcuts overlay
and all 5 i18n locales.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Floating button appears after scrolling 400px, respects reduced motion
preference. T key scrolls to top from anywhere. Both registered in the
keyboard shortcuts overlay with i18n support across all 5 locales.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Introduce a role-based access control system that allows lecturers to
lock and unlock course content at runtime. Lecturers are identified by
matching their GitHub login against owner/lecturers properties set in
the course configuration.

- Add isLecturer, courseLecturers, and contentLocks reactive runes
- Extract owner/lecturers from course.properties on course load
- Create RBAC service with lock state management (Supabase + localStorage fallback)
- Add Supabase client functions for content lock CRUD and learning records query
- Add lock overlay on Cards and Units (greyed out with lock icon for students)
- Add inline lock toggle buttons visible only to lecturers
- Create LecturerButton nav component and LecturerPanel sidebar with
  content locks tree, enrollment viewer, and access analytics tabs
- Add route guard to prevent direct navigation to locked content
- Add lock, unlock, and lecturer icons to all four theme icon sets
- Add L keyboard shortcut to toggle lecturer/student view in dev mode

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
@vercel

vercel Bot commented Jul 23, 2026

Copy link
Copy Markdown

@lgriffin is attempting to deploy a commit to the Jordan Harrison Team on Vercel.

A member of the Team first needs to authorize it.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant