A platform for authoring step-by-step coding labs and letting learners work through them at their own pace with progress tracking. Built with Next.js 16 (App Router) and Supabase (Postgres, Auth, Storage).
- You are the sole author/admin: create, edit and publish labs through a rich WYSIWYG editor.
- Anyone can sign up to read along and track their progress (per-step completion + resume where they left off).
- Embed interactive simulations in any step — animated architecture diagrams and process walkthroughs authored with a visual drag-and-connect builder and played back with guided stages + free pan/zoom.
- Cursor-inspired light/dark theme.
- Next.js 16 (App Router, Server Components, Server Actions)
- Supabase: Postgres + Row Level Security, Auth (email + GitHub/Google OAuth), Storage
- Tailwind CSS v4, Radix primitives, Tiptap editor (with syntax-highlighted code blocks)
- React Flow (
@xyflow/react) for the interactive simulation canvas next-themes,zod,lowlight
At supabase.com, create a project. Then in the SQL editor run the migrations in order:
supabase/migrations/0001_init.sql— tables, RLS, triggers,is_admin()supabase/migrations/0002_storage.sql— the publiclab-assetsbucket + policiessupabase/migrations/0003_step_templates.sql— reusable step-content templatessupabase/migrations/0004_public_profile.sql— aggregated activity/completed-lab functions for public profilessupabase/migrations/0005_modules_hints.sql— step modules, per-step hints, and the learner hints preferencesupabase/migrations/0006_simulation_library.sql— the reusable simulation library (simulationstable)
In Authentication → Providers, enable GitHub and Google and add their
client IDs/secrets. Add http://localhost:3000/auth/callback (and your prod URL)
to the provider redirect/callback allow-lists and to URL Configuration →
Redirect URLs.
Copy .env.local.example to .env.local and fill in from Project Settings → API:
NEXT_PUBLIC_SUPABASE_URL=...
NEXT_PUBLIC_SUPABASE_ANON_KEY=...
NEXT_PUBLIC_SITE_URL=http://localhost:3000
npm install
npm run devOpen http://localhost:3000.
Sign up once through the app (this creates your profiles row via a trigger),
then in the Supabase SQL editor run:
update public.profiles
set role = 'admin'
where id = (select id from auth.users where email = 'you@example.com');Reload the app — you'll now see the Author link and can create labs at /admin.
| Area | Path |
|---|---|
| Landing | src/app/page.tsx |
| Public catalog (search + tags) | src/app/labs/page.tsx |
| Lab overview (start/resume) | src/app/labs/[slug]/page.tsx |
| Step viewer (read-along + mark complete) | src/app/labs/[slug]/steps/[position]/page.tsx |
| Public profile (activity graph + completed labs) | src/app/u/[id]/page.tsx |
| Admin authoring | src/app/admin/** |
| Reusable step templates | src/app/admin/templates/** |
| Image pool + template pickers (editor) | src/components/editor/media-library.tsx, template-picker.tsx |
| Interactive simulations (Tiptap node + builder/player) | src/lib/simulation/*, src/components/simulation/*, src/lib/editor/simulation-extension.ts |
| Reusable simulation library (save once, insert anywhere) | src/lib/actions/simulations.ts, src/components/editor/simulation-picker.tsx |
| Auth | src/app/(auth)/login, src/app/auth/callback, src/app/auth/confirm |
| Supabase clients / session proxy | src/lib/supabase/*, src/proxy.ts |
| Data access | src/lib/queries.ts |
| Server Actions | src/lib/actions/* |
| Schema | supabase/migrations/* |
Security is enforced by Postgres Row Level Security: drafts and authoring are
restricted to the admin via is_admin(), and each learner can only read/write
their own progress rows.
Deploy to Vercel, set the same env vars (with NEXT_PUBLIC_SITE_URL = your
production origin), and add https://your-domain/auth/callback to Supabase's
redirect URLs and each OAuth provider.