Skip to content

Repo size audit (16.10.2026) ​

Owner 16.10.2026 (SRC-1422): bring nemo12-www down to about 5 MB and nemo12.com to about 10 MB, audit first. Measured on the state right after the repo split (16.10.2026): nemo12-www with its open PRs #1-#4, nemo12.com on session/repo-split (www and Pearl already removed, otherwise equal to main).

Verdict. nemo12-www can reach about 5.5 MB, and 5 MB once the CMS (phase 2 of the split) owns www content. nemo12.com reaches about 36 MB by taking media, SQL, migrations and content out of git (and landing the removals already in flight); about 17 MB once docs.nemo12.com has its own repo and the eleven extra apps are out or retired; about 12-14 MB with generated E2E fixtures and archived one-off scripts. What remains is code and tests, which should stay: exactly 10 MB would mean cutting code itself.

Two sizes, two different fixes ​

Checkout (tracked files at HEAD)Clone (git history, packed)
nemo12-www34.7 MB, 1,433 files12.3 MB
nemo12.com161.9 MB, 5,623 files (190 MB, 6,482 files before the split)147.7 MB

Removing files shrinks the checkout at once. The clone keeps every old version until history is rewritten (section "Git history"). node_modules (707 MB and about 810 MB) is not in git and is not counted.

nemo12-www: 34.7 MB to about 5 MB ​

Every tracked file sits in exactly one bucket:

BucketMBWhatFix
Generated seed SQL15.46scripts/seed-seo-pages.sql 6.05, four seed-articles-*.sql 8.17, seed-illustrations.sql 1.26Stop committing: the seed-data workflow builds them from source right before loading
Content8.85400 article Markdown files 3.93, SEO pages 0.96, docs/curriculum 1.91, illustration registry + alts 1.42, books content 0.88CMS phase 2: content lives in D1 nemo12-cms, edited in cms.nemo12.com
Code3.73apps, worker, scripts, packagesKeep
Images2.70social covers 2.15 (cover-youtube.png 0.81 ...), article photos 0.55R2 (nemo12-content), served from the media route
Contract snapshots2.34openapi.snapshot.json 1.22, seed-videos.sql 0.74Keep only what tests read: the path list (about 30 KB) and the video rows (about 50 KB)
Other1.44package-lock.json 0.52, config, SVGKeep
Tests0.21Keep
StepSavesSize afterRisk
1. Generated seeds out of git15.519.3Low: one workflow change; the --check gates move into it
2. Slim contract snapshots1.917.4Low
3. Images to R22.714.7Low: URLs change, the SEO gate checks them
4. CMS phase 2 (content to D1)8.9about 5.8Medium: the planned phase 2 itself
5. Large copy files in src/site (subjectCopy.ts, students.ts ...) to CMSabout 0.8about 5.0Medium

nemo12.com: 161.9 MB to about 10-12 MB ​

BucketMBWhatFix
Media52.1455 MP3 in apps/learn/public/audio 38.6, JPG 13.1 (apps/learn/public/img 10.2, compass 2.9), PNG 0.4 (learn's are in R2 since 17.10.2026)R2 nemo12-content, served like the videos already are
Seed and archive SQL21.566 scripts/*.sql 19.4 (seed-b21 3.0, seed-parent-bodies-* 7.1, seed-parent-gates-* 4.4, seed-grammar 1.3 ...), the AI Teen scripts folder 1.3 (removed by SRC-1419), scripts/archive 0.8Generated ones: build at seed time. Already-loaded one-offs: archive to R2 with their run date
Migrations20.2358 files; the big ones load content (0294 1.75, 0280 1.72, 0265 1.10 ...)Squash into one baseline schema: 374 tables = 252 KB. Content goes to seeds; tests get small fixtures
Content data15.6scripts/course-content 6.9, apps/learn/src/**/*.json 4.9, content/ 3.7, scripts/b21 1.2 ...D1 (it is already the source of truth for IELTS content), edited in Dolphin (SDD-056)
In-flight removals14.5math (the learn math folder, course content), AI Teen, b21 (math and AI Teen removed by SRC-1419)Already claimed by other sessions (toan12-split, english-only-cleanup, b21-redirect)
Apps not in the owner's list8.8marlins 6.9 (5.8 of it parent lessons and ebook chapters as .ts, the same text again in seed-parent-*.sql), compass, ui, coral, gull, mm, partners, tutors, reef, ielts, playbooksOwner decision: own repo(s), or retire
Docs9.9docs.nemo12.comOwn repo (nemo12-docs), like www
Code11.1learn, api, admin, dolphin, docs app, packages, scriptsKeep; one-off scripts can be archived
Tests and E2E fixtures4.5api tests 1.9, learn E2E 2.3 (content.fixture.json 0.9)Keep; generate the big fixtures
Other1.4lock, configKeep
Content as code TS2.2explore/configs.tsx 0.24, shared/prompts.ts 0.15 ...D1
StepSavesSize afterRisk
1. Media to R252.1109.8Low-medium: a media route, URL rewrite, e2e of audio pages
2. Seed and archive SQL out of git21.588.3Low
3. Squash migrations (baseline + test fixture; the baseline runs once on production as a no-op)20.068.3Medium: migrate:check and api tests move to the baseline
4. Land the in-flight removals (math, AI Teen, b21)14.553.8Owned by other sessions
5. Content data and content-as-code to D117.836.0Medium-high: content editing moves to Dolphin
6. Docs to their own repo9.926.1Medium, same recipe as the www split
7. The eleven extra apps out or retired8.8about 17.3Owner decision per app
8. Generate big E2E fixtures, archive one-off scriptsabout 3-5about 12-14Low

Exactly 10 MB would mean cutting code itself. The audit recommends stopping at about 12-14 MB.

Git history ​

TodayAfter rewriting history to drop media and SQL blobs
nemo12-www12.3 MB (SQL 2.6, PNG 2.4, MD 2.6)about 5 MB
nemo12.com147.7 MB (MP3 34.5, JPG 22.5, SQL 15.5, PNG 14.9, MD 11.7, TS 11.2)about 30-40 MB

A rewrite force-pushes main and invalidates every open branch, ready/* branch and worktree (10 ready/* branches and 8 claimed tasks today). Plan:

  • nemo12-www: rewrite now, before anyone else depends on it: its only branches are the split's own.
  • nemo12.com: rewrite once, last, at a quiet moment: after steps 1-3, with every session stopped and every open branch merged or rebased.

Order and guardrails ​

  1. nemo12-www steps 1-3, plus its history rewrite.
  2. nemo12.com steps 1-3 (media, SQL, migrations): 94 MB out at low risk.
  3. CMS phase 2 (nemo12-www step 4) and nemo12.com step 5 (content to D1 via Dolphin).
  4. Owner decisions: docs repo, extra apps.
  5. nemo12.com history rewrite.

A gate stops regrowth in both repos: no new tracked media file (.mp3, .m4a, .jpg, .png, .webp), no new generated scripts/seed-*.sql, and no tracked file over 500 KB without an allow-list line with a reason.

Progress ​

DateStepResult
17.10.2026nemo12-www steps 1-334.7 to 16.5 MB (nemo12-www PRs #5, #6)
17.10.2026Unused D1 data archived to R2 and droppedmigration 0359, PR #714 (see data-audit)
17.10.2026nemo12.com step 2, seeds without test readers7.5 MB out, PR #715
17.10.2026nemo12.com step 1, NEMO WALK media to R248.8 MB out: 549 files verified by sha256 from production, served by GET /v1/public/media/walk/... (PR #716 and the learn PR)
17.10.2026nemo12.com step 3, migrations to a baseline359 files (20.2 MB) became 0000_baseline.sql (483 KB) plus workers/api/test/reference-rows.sql (848 KB of test rows): 18.9 MB out, checkout 124.6 to 105.7 MB. On the bare baseline 102 of 3,250 api tests failed, all for missing reference rows; the fixture brings them back. Production schema read 17.10.2026: all 732 baseline objects already exist there, so the baseline's one run is a no-op
17.10.2026Bank-wide IELTS content checks back, on production dataThe squash left the api tests a six-skill slice. Nightly job ielts-bank-check (see below) now checks the whole bank

Checks on content that lives only in production ​

After step 3, production D1 is the only copy of the IELTS micro-skill bank (51 skills, about 5,000 items), edited through seed-data or Dolphin. The api tests that used to check the whole bank now see the slice in workers/api/test/reference-rows.sql. The nightly workflow .github/workflows/ielts-bank-check.yml (22:30 UTC, also workflow_dispatch) covers the rest:

  • It exports ielts_task_types, ielts_micro_skills, ielts_micro_exercises and ielts_micro_skill_items with wrangler d1 export (read-only) into SQLite.
  • scripts/check-ielts-bank.mjs --db <file> runs the rules the tests enforced up to SRC-1422: 51 skills per area, at least 5,008 items, every answer index within distinct options, every warm-up set showing 3 items, four stages per skill and their languages, at least 4 items per skill with exercises, at least 3 exercises per level for Listening, Speaking and Writing, plus reference and task-type checks.
  • scripts/audit-content.mjs --db <file> scores completeness; it now fails when the D1 part cannot be read.

A red run means production content broke a rule: fix the rows through seed-data or Dolphin. Adding a skill or retiring items on purpose means editing the floor in check-ielts-bank.mjs.

How to measure again ​

bash
git ls-files -z | xargs -0 stat -f '%z' | awk '{s+=$1} END {printf "%.1f MB\n", s/1048576}'
git count-objects -vH | grep size-pack