1# plyr.fm Developer Context 2 3**music streaming on AT Protocol** 4 5## Reminders 6- i am already hot-reloading the backend and frontend. i might also have ngrok exposing 8001 7- check the justfiles. there's a root one, one for the backend, one for the frontend, and one for the transcoder etc 8 9## 🚨 Critical Rules & Workflows 10* **Read `STATUS.md` First:** Always check for active tasks and known issues. 11* **Workflow:** 12 * Use **GitHub Issues** (not Linear). 13 * **PRs:** Always create for review; never push to main directly. 14 * **Deploy:** Automated via Actions (Backend: Fly.io, Frontend: Cloudflare Pages). Never deploy locally. 15* **ATProto NSIDs:** namespaces are environment-aware via settings (e.g., `fm.plyr.dev` (dev), `fm.plyr` (prod)). **Never** hardcode outside of scripts. these are fully-qualified hostname in Reverse Domain-Name Order, not urls. 16* **Auth Security:** Session IDs live in HttpOnly cookies. **Never** touch `localStorage` for auth. 17* **Async Everywhere:** Never block the event loop. Use `anyio`/`aiofiles`. 18* **Type Hints:** Required everywhere (Python & TypeScript). 19* **Communication:** Use emojis sparingly and strictly for emphasis. 20* **DO NOT UNNECESSARILY DEFER IMPORTS.** Put imports at the top of the file where they belong. Deferred imports inside functions are only acceptable for avoiding circular imports - not for "lazy loading" or other reasons. 21 22## 🛠️ Stack & Tooling 23* **Backend:** FastAPI, Neon (Postgres), Cloudflare R2, Fly.io. 24* **Frontend:** SvelteKit (Svelte 5 Runes), Bun, Cloudflare Pages. 25* **Observability:** Logfire. 26* **`just` use the justfiles!** 27* **use MCPs** for access to external systems, review docs/tools when needed 28 29### Neon Serverless Postgres 30- `plyr-prd` (cold-butterfly-11920742) - production (us-east-1) 31- `plyr-stg` (frosty-math-37367092) - staging (us-west-2) 32- `plyr-dev` (muddy-flower-98795112) - development (us-east-2) 33 34## 💻 Development Commands 35* **Backend:** `just backend run` 36* **Frontend:** `just frontend run` 37* **Tests:** `just backend test` (run from repo root, not from backend/) 38* **Linting:** `just backend lint` (Python) / `just frontend check` (Svelte) 39* **Migrations:** `just backend migrate "message"` (create), `just backend migrate-up` (apply) 40 41## 📂 Project Structure 42``` 43plyr.fm/ 44├── backend/ 45│ └── src/backend/ 46│ ├── api/ # Public endpoints 47│ ├── _internal/ # Auth, PDS, Uploads logic 48│ ├── models/ # SQLAlchemy schemas 49│ ├── storage/ # R2 and filesystem adapters 50│ └── utilities/ # Config, helpers 51├── frontend/ # SvelteKit app 52│ ├── src/routes/ # Pages (+page.svelte, +page.server.ts) 53│ └── src/lib/ # Components & State (.svelte.ts) 54├── scripts/ # Admin scripts (uv run scripts/...) 55├── docs/ # Architecture & Guides 56└── STATUS.md # Living status document 57``` 58 59this file ("AGENTS.md") is symlinked to `CLAUDE.md` for maximal compatibility.