Next.js 16 app for planning semesters, subjects, assignments, todos, and exam sprints.
- Next.js 16
- React 19
- Clerk for auth
- Drizzle ORM
- MySQL (
mysql2)
Copy .env.example to .env.local and fill in the values you actually use.
Required in production:
DATABASE_URLNEXT_PUBLIC_CLERK_PUBLISHABLE_KEYCLERK_SECRET_KEY
Optional for local development:
DB_HOSTDB_PORTDB_USERDB_PASSWORDDB_NAME
DATABASE_URL is the preferred setting everywhere. The split DB_* variables are only kept as a local fallback.
npm install
npm run devOpen http://localhost:3000.
Generate a migration after schema changes:
npm run db:generateApply migrations to the target database:
npm run db:migratePush schema changes directly without generating SQL first:
npm run db:pushOpen Drizzle Studio:
npm run db:studioThis app is ready to deploy to Vercel.
Use a managed MySQL database. For your current plan, use Aiven and copy the exact DATABASE_URL they provide for the MySQL service.
If your Aiven service requires SSL, also add the CA certificate contents as DATABASE_SSL_CA. The app and Drizzle tooling now support that directly.
Add these in the Vercel project settings:
DATABASE_URLDATABASE_SSL_CAif Aiven requires TLS verificationDATABASE_SSL_REJECT_UNAUTHORIZEDwith valuetrueNEXT_PUBLIC_CLERK_PUBLISHABLE_KEYCLERK_SECRET_KEY
Add UploadThing keys only if you enable uploads in production.
Before the first production release, run:
npm run db:migrateRun it against the production DATABASE_URL so the tables exist before the app starts serving traffic.
This repo also includes a GitHub Actions workflow that can run the same migration automatically after a successful Vercel production deployment, plus a manual dispatch option for controlled releases.
- Add your Vercel production URL to Clerk allowed origins / redirect URLs.
- Use the production Clerk keys in Vercel.
- Import the repo into Vercel.
- Keep the default build command:
npm run build - Keep the default install command:
npm install
The repo includes .github/workflows/production-db-migrate.yml.
It runs database migrations in two cases:
- manually through
workflow_dispatch - automatically after a successful GitHub
deployment_statusevent for theProductionenvironment
Set these GitHub environment secrets in the production environment:
DATABASE_URLDATABASE_SSL_CAif your Aiven service requires TLS verificationDATABASE_SSL_REJECT_UNAUTHORIZEDwith valuetrue
For schema changes that are not backward-compatible, use the manual workflow before or alongside the production rollout instead of relying only on the post-deploy trigger.
- The app builds successfully in production mode.
- The repo now supports a single
DATABASE_URLfor runtime and Drizzle tooling. - The runtime and Drizzle config both support optional SSL settings for managed MySQL providers like Aiven.