Lesson 0006 · ~12 minutes
One skill: name the failure modes that turn a monorepo into a slower polyrepo — and the moon-shaped counters you already know.
In a design review you can reject “dump folders in git and hope,” flag full-CI thrash, missing ownership, and cache lies — and know when polyrepo is still the right call.
Nx and monorepo.tools both insist: multiple projects in one repo without well-defined relationships is not a real monorepo — it is collocation. Symptom: every PR runs every test; nobody knows the graph. Counter: moon project graph + tasks + targets (lessons 2–4).
Cost scales with repo size, not change size. moon’s
--affected (and graph-fed CI) only runs work whose inputs
intersect VCS changes
(run a task). Without
that, monorepos lose to many small polyrepo pipelines.
Google’s monorepo paper lists
unnecessary dependencies and code-health cost as first-class
downsides
(CACM). Easy imports become spaghetti. moon’s
constraints.enforceLayerRelationships and
tagRelationships in
workspace config
exist to fail the graph when layer/tag rules break — use them before the
tangle hardens.
One repo does not mean one team. Without CODEOWNERS / project
owners, reviews become random and drive-by breaks land
unowned. moon can aggregate owners and sync CODEOWNERS
((codeowners). Polyrepo “repo = team” was ownership for free — monorepos must buy it
back.
Smart hashing only helps if inputs/outputs match reality. Missing inputs → stale green. Phantom outputs → broken hydration. Inheritance without inputs (lesson 4) re-creates “always run.” Treat cache correctness as a product requirement, not a bonus.
Shared tasks on different Node majors is not standardization. Lesson 5:
pin with .moon/toolchains + full semver; use force-globals
only when CI/Docker already owns the binaries.
History, CI secrets, permissions, and habits do not vanish on
moon init. Prefer incremental adoption; moon documents
migrate helpers from Nx/Turborepo
(setup workspace
/ extensions). Big-bang “merge all repos this Friday” is a deal-breaker
unless the org already pays for a platform team.
Then polyrepo (or a later synthetic monorepo graph) is the honest choice — lesson 1 spectrum still holds.
A monorepo without graph, affected CI, ownership, and pins is often worse than polyrepo. Tooling is not optional décor.
Equal-length options. Spot the deal-breaker fast.
Five apps land in one git root with ad-hoc scripts; CI runs all tests always. Best label?
Apps start importing each other’s private internals freely. First moon-shaped counter?
Strongest reason to keep polyrepo instead of monorepo?
Builds report cache hits but miss real source edits. Likeliest cause?
Recommended: re-skim What is a Monorepo? (collocation vs tooling) and the advantages/costs section of Google’s CACM monorepo paper. Keep the deal-breakers sheet for reviews.