| Component | Version | Notes |
|---|---|---|
| Next.js | 16.2.2 | App Router, Turbopack |
| React | 19.2.0 | Server Components |
| Prisma | 7.2.0 | SQLite via libsql adapter |
| DB | SQLite | File: ./prisma/dev.db |
| tRPC | 11.6.0 | superjson transformer |
| better-auth | 1.5.6 | Auth provider |
| Tailwind | 4.1.14 | CSS-first (no .config.js) |
| Biome | 2.3.0 | Lint + format |
| Zod | 4.1.12 | Validation |
# DB (SQLite — DATABASE_URL required)
DATABASE_URL="file:./prisma/dev.db" pnpm db:push # Sync schema to DB
pnpm prisma generate # Regenerate client
pnpm seed:minimal # Seed with minimal preset
pnpm seed --preset=vitro-rojas-panama # Real client data
# Dev
pnpm dev # Next dev with turbo
pnpm build # prisma generate && next build
# Quality
pnpm lint:errors # Biome errors only
pnpm typecheck # tsc --noEmit
pnpm test # VitestGenerated to prisma/generated/client, NOT node_modules/@prisma/client. Import from generated path:
import { PrismaClient } from "./generated/client"Uses @prisma/adapter-libsql + @libsql/client. Config in prisma.config.ts. The DATABASE_URL env var or fallback file:./prisma/dev.db is used.
This field is a JSON string (not an array) due to SQLite limitations. When reading: JSON.parse(model.compatibleGlassTypeIds). When writing: JSON.stringify(array). 30+ files in the codebase still assume it's an array — this is a known architectural debt.
Account/Session models use @map() for legacy NextAuth compatibility. Don't remove these.
minimal— CI/testing onlyvitro-rojas-panama— Primary client (Panama aluminum windows)vidrios-la-equidad-colombia— Secondary clientdemo-client,full-catalog— Other presets
- compatibleGlassTypeIds: Mismatch between schema (String/JSON) and codebase (expects String[]). See
openspec/changes/migrate-sqlite-compatible-glass-array/proposal.md - better-sqlite3 won't compile on Node 25. Use
@libsql/client+@prisma/adapter-libsqlinstead. - Schema-seeders drift: TenantConfig schema may not match what seeders expect. Check fields before running seeds.
prisma/
├── schema.prisma # Schema fuente
├── generated/client/ # Prisma client generado (READ ONLY)
├── migrations/ # Versioned migration history
├── migrations-scripts/ # One-off migration utilities
├── seeders/ # Individual seeders
├── seed-cli.ts # Seed orchestrator CLI entry point
├── factories/ # Test data generators
├── data/
│ ├── catalog/ # Reference catalog data
│ ├── clients/ # Per-client reference data
│ │ └── vitro-rojas/ # Client: Vitro Rojas Panama
│ └── presets/ # Seed presets per client
├── check-user.ts # Utility: lookup user by email
└── test-password.ts # Utility: test password hashing
src/
├── server/
│ ├── db.ts # Prisma client singleton
│ └── api/routers/ # tRPC routers
├── domain/ # Business logic
└── app/ # Next.js App Router
DATABASE_URL=file:./prisma/dev.db # SQLite path (required for prisma commands)
- Don't
import { PrismaClient } from "@prisma/client"— use the generated client - Don't assume
compatibleGlassTypeIdsis an array — it's a JSON string - Don't use
better-sqlite3directly — use@libsql/client - Don't edit
prisma/generated/client/— it's generated - Don't use comments this lied the code not
- Condigo autodocumentado, no se necesitan comentarios adicionales. Si algo no es claro, es un indicativo de que el código podría ser refactorizado para mejorar su legibilidad.