How I structure Next.js projects for internal systems
A pragmatic folder structure and data layer that scales from MVP to production without rewrites.
#Introduction
Internal systems outlive their first version. The structure that gets you to demo day is rarely the one that survives year two, so I now start every build with the same boring, proven shape.
#Feature folders over type folders
Grouping code by feature (inventory, orders, auth) instead of by type keeps every change local. When a client asks for one more column in a table, everything I touch lives in one folder — and removing a feature is a folder delete, not an archaeology dig.
#The data layer
Components never import the database client directly; all access goes through server actions inside the feature folder. That single rule keeps permissions auditable in one place — exactly what an internal system gets audited on.
#Wrapping up
None of this is clever, and that is the point. Boring structure means a new developer ships in week one, and the system stays maintainable when it quietly becomes business-critical.
src/
app/(dashboard)/inventory/page.tsx
features/inventory/
api/ # server actions
components/ # tables, forms
hooks/
lib/db.ts # one Prisma instance