# Contributing

> How to contribute to Moonspell, what is in the public repo, which checks to run before a pull request, where plans and issues live, and the rules that keep every game playing everywhere.

Moonspell is open source under the MIT License: the engine and game template, the examples, the skills, the server with Nova and the worker runs, the edge Worker, the contracts, the specs and these docs. The Moonspell phone app and the bundling CLI are private ([What is open and what is private](https://docs.moonspell.app/start/open-source.md)). Contributions to any public part are welcome.

## How to contribute

1. For anything bigger than a small fix, open an issue first and describe the change. It saves building something that cannot be merged.
2. Fork the repository and create a branch from `main`.
3. Keep the change focused: one fix or one feature per pull request.
4. Run the checks for every folder you touched (below) and say in the pull request what you ran.
5. A maintainer reviews it.

The root `CONTRIBUTING.md` says the same in short.

## The public tree

| Path | What it is |
|---|---|
| `templates/crescent-game/` | The engine (`src/engine/`), the starter game Sunset Sprint (`src/game/`), the example games (`examples/`), and the `CLAUDE.md`, `AGENTS.md`, `.claude/skills/` and `docs/` a coding agent reads. Every game repo starts as a copy of it. See [Engine overview](https://docs.moonspell.app/engine/overview.md) |
| `agent/` | Nova, the chat agent (eve). See [Nova and the worker](https://docs.moonspell.app/moonspell/nova-and-the-worker.md) |
| `src/workflows/` | The game-run and cover workflows |
| `src/lib/` | Server logic: the sandbox and run script (`daytona.ts`), games, repos, realtime tokens, credits, community builds, sign-in |
| `src/app/` | Next.js routes: the app API (`api/app/`), internal routes (`api/internal/`), the web app (`(app)/`), the shared-game page (`g/`), the game page (`w/`), well-known files |
| `src/web/` | The web app's client code |
| `edge/` | The Cloudflare Worker in front of the server. See [Live progress](https://docs.moonspell.app/moonspell/realtime.md) |
| `db/` | Postgres migrations and `migrate.mjs` |
| `contracts/`, `spec/` | What the three apps share, and every app behaviour with a column per app. See [Three apps, one product](https://docs.moonspell.app/moonspell/three-apps.md) |
| `scripts/` | Operational scripts: the sandbox snapshot, starter upload, backfills, asset generation, playtests. Those that export games need the private CLI |
| `playtests/` | Playtest scripts for older games that predate `playtest.json` |
| `docs/`, `docs-site/` | These docs, and the Docusaurus site that renders them |
| `.scratch/` | Plans and issues (below) |

## Checks before a pull request

All of these are real scripts in the repo's `package.json` files.

| You changed | Run | Where |
|---|---|---|
| The engine, the template, an example | `npm run typecheck`, `npm test`, `npm run export:web` | `templates/crescent-game/` |
| The server, Nova, the workflows, the web app | `npm run typecheck`, `npm run lint`, `npm test`, `npm run build` | repo root |
| The edge Worker | `npm run typecheck` (and `npm test` at the root, which runs its tests) | `edge/` |
| The backend scaffold | `npm run typecheck`, `npm run smoke` against `wrangler dev` | the scaffold's `backend/` |
| Contracts | `npm run contracts`, then `npm run contracts -- --check` | repo root |
| Feature specs | `npm run parity` | repo root |
| Docs | `npm --prefix docs-site run build` | repo root |

A change to how a game looks or plays should also be played in a browser with `npm run web` in the template. More detail per part is in [Testing](https://docs.moonspell.app/moonspell/testing.md).

## Plans and issues

Bug reports and ideas go in the repository's issues. Larger pieces of work are planned in Markdown under `.scratch/`:

- one folder per feature, `.scratch/<feature-slug>/`;
- the plan is `.scratch/<feature-slug>/PRD.md`;
- issues are `.scratch/<feature-slug>/issues/<NN>-<slug>.md`, numbered from `01`;
- each issue has a `Status:` line near the top: `needs-triage`, `needs-info`, `ready-for-agent`, `ready-for-human`, `wontfix`, or `done` with a line saying how it was verified.

What is planned next for the engine is in the [Roadmap](https://docs.moonspell.app/contributing/roadmap.md).

## Rules

**A game is written once and plays on the web, iOS and Android.** What differs per platform belongs in the engine (`*.web.ts` files, `Platform.OS` checks), never in a game and never in one app. If a game needs a platform workaround, the fix goes into the engine so every game gets it. See [Platform layer](https://docs.moonspell.app/engine/platform-layer.md).

**The template is the production template.** The hosted Moonspell worker makes every new game from `templates/crescent-game/`, and on each run it copies the template's engine, skills, docs, examples, `CLAUDE.md` and package files into existing games, for every file their builder never changed. A change there reaches every game on its next build. So:

- keep changes additive and backwards compatible;
- do not rename or remove scripts, skills, files or exports that games may use;
- do not change engine behaviour that games rely on without a plan in `.scratch/`;
- keep the template's own docs and skills in step with the code they describe.

**Game data lives on the game's own backend.** Leaderboards, rooms and saves use the backend scaffold in `templates/crescent-game/.claude/skills/realtime-backend/scaffold/backend/`, never a third-party data service. See [Backend overview](https://docs.moonspell.app/backend/overview.md).

**The app's native surface is fixed.** A game cannot add native code: the template's `package.json` pins the native modules the Moonspell app ships. Pure JavaScript packages are fine.

**Generated files are never edited by hand.** For example `src/web/generated/`: change `contracts/` and run `npm run contracts`.

**Docs are true or they are not written.** Every name, prop, command and path on a page matches the source. Code samples come from, or are checked against, `templates/crescent-game/src` and `examples/`. Pages are MDX: keep placeholders and braces inside code. Short sentences, plain words, no emoji.

**Design is monochrome.** Black, white and grays, in the docs, the web app and the engine's default UI.
