# Admin / CRM — Next.js (templates2) A **ready-to-run** internal tool built on the v2 Next.js base: an entity registry (Customers, Deals) with CRUD, roles, CSV import/export and an audit log. Everything works on the first run — SQLite + mock providers need no keys. ## Quickstart ```bash npm ci cp .env.example .env # SQLite + mock providers by default — no keys needed npm run db:setup # prisma db push + seed (20 customers, 15 deals, audit trail) npm run dev # http://localhost:3000/admin ``` ## Demo accounts (seeded) | Role | Email | Password | Can do | |---|---|---|---| | admin | `admin@example.com` | `password` | read, create/edit, delete, import/export | | editor | `editor@example.com` | `password` | read, create/edit, import/export | | viewer | `viewer@example.com` | `password` | read only | Roles are enforced **server-side** on every admin API route (`lib/server/guard.ts` + `lib/rbac.ts`); the UI merely hides what a role cannot do. ## What this case adds on top of the base - **Entity registry** — `Customer` and `Deal` with list (search, column filter, sort, pagination), detail, create/edit and delete (delete asks for confirmation). `components/admin/CustomersManager` and `DealsManager` drive the `/admin/customers` and `/admin/deals` pages. - **Dashboard** — counters (customers, leads, deals, won value), a deals-by-stage bar chart and recent activity on `/admin` (`lib/server/crm.ts#overview`). - **CSV import** — `/admin/import` validates a CSV, shows a per-row error report and a preview of the first valid rows, then commits. Export is a `text/csv` download. - **Audit log** — every mutation writes an `AuditLog` row (`lib/server/audit.ts`); `/admin/audit` lists it and filters by action. - **Loading / empty / error states** on every list and the import wizard. ## API | Method | Path | Role | |---|---|---| | GET | `/api/admin/customers?q=&status=&sort=&page=` | viewer+ | | POST | `/api/admin/customers` | editor+ | | GET / PATCH / DELETE | `/api/admin/customers/:id` | viewer+ / editor+ / admin | | GET / POST | `/api/admin/deals` | viewer+ / editor+ | | PATCH / DELETE | `/api/admin/deals/:id` | editor+ / admin | | POST | `/api/admin/import/customers` (`{ csv, commit }`) | editor+ | | GET | `/api/admin/export/customers` | viewer+ | | GET | `/api/admin/audit?action=` | viewer+ | ## Data model `prisma/schema.prisma`: the base `User`, `Session`, `Subscription`, `AuditLog` plus `Customer` and `Deal`. SQLite in development; point `DATABASE_URL` at Postgres for production. ## Quality ```bash node ../templates2/qa.mjs Admin.Next # from the repo root: node templates2/qa.mjs Admin.Next ``` The harness runs validate → clone → install → lint → typecheck → unit → build → boot → routes → e2e → screenshot. See [`../CONTRACT.md`](../CONTRACT.md) for the Definition of Done.