CodingNic

Defining Models and Migrations

Your First Migration

Defining Models and Migrations 15 min read

Your First Migration

Objectives

By the end of this lesson, you should be able to:

  • Run prisma migrate dev and explain what it does
  • Locate and read a generated migration file
  • Confirm a migration actually created a table in the database

๐Ÿ’ก Why this matters: Every model written so far exists only in schema.prisma, nothing has touched the actual database. This lesson closes that gap, turning a schema into real tables, tracked and versioned.

โš ๏ธ A note on verification: as throughout this module, the Prisma CLI can’t run inside this course’s own sandboxed tooling (no route to its engine download). The commands and output below reflect Prisma’s stable, current, documented behavior. Run them yourself, on your own machine, against your own database, they’ll behave exactly as shown.

Running the Migration

Starting from the Student model in the last lesson:

bash
npx prisma migrate dev --name init
text
Environment variables loaded from .env
Prisma schema loaded from prisma/schema.prisma
Datasource "db": PostgreSQL database "school", schema "public" at "localhost:5432"

Applying migration `20260101120000_init`

The following migration(s) have been created and applied from new schema changes:

migrations/
  โ””โ”€ 20260101120000_init/
    โ””โ”€ migration.sql

Your database is now in sync with your schema.

โœ” Generated Prisma Client (v7.x.x) to ./node_modules/@prisma/client in 48ms

--name init names the migration, migrations are numbered by timestamp, so the exact folder name reflects when it ran. Notice the last line, prisma migrate dev calls prisma generate automatically, no separate step needed.

Project File Structure After Migrating

text
prisma-intro/
โ”œโ”€โ”€ package.json
โ”œโ”€โ”€ .env
โ”œโ”€โ”€ prisma/
โ”‚   โ”œโ”€โ”€ schema.prisma
โ”‚   โ””โ”€โ”€ migrations/
โ”‚       โ””โ”€โ”€ 20260101120000_init/
โ”‚           โ””โ”€โ”€ migration.sql
โ””โ”€โ”€ node_modules/

Reading the Generated Migration File

sql
-- migrations/20260101120000_init/migration.sql
-- CreateTable
CREATE TABLE "Student" (
    "id" SERIAL NOT NULL,
    "name" TEXT NOT NULL,
    "grade" INTEGER NOT NULL,
    "email" TEXT,
    "enrolledAt" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,

    CONSTRAINT "Student_pkey" PRIMARY KEY ("id")
);

-- CreateIndex
CREATE UNIQUE INDEX "Student_email_key" ON "Student"("email");

This is real, plain SQL, CREATE TABLE, PRIMARY KEY, CREATE UNIQUE INDEX, generated directly from the schema in the last lesson. SERIAL for the auto-incrementing ID, TIMESTAMP(3) DEFAULT CURRENT_TIMESTAMP for @default(now()), a nullable TEXT for the optional email field, everything traceable straight back to Module 1’s raw SQL.

Confirming It Worked

Connect with psql (Module 1, Lesson 2) and check:

sql
\dt
text
         List of relations
 Schema |    Name    | Type  |  Owner
--------+------------+-------+----------
 public | Student    | table | postgres

The table exists in the real database now, created entirely from the schema file, no hand-written CREATE TABLE needed.

Migration History Is Tracked

Prisma also creates a _prisma_migrations table in the database itself, recording which migrations have already been applied. Running prisma migrate dev again with no schema changes does nothing, it already knows this migration ran.

Try It

  1. Run prisma migrate dev --name init against your own Student model from the last lesson.
  2. Open the generated migration.sql file, and match every line back to a field or attribute in your schema.
  3. Connect with psql, and confirm the table exists with \dt and \d "Student".
  4. Run prisma migrate dev a second time with no schema changes, and observe that it reports nothing to do.

Recap

  • prisma migrate dev --name <name> generates a SQL migration file from schema changes, applies it to the database, and regenerates Prisma Client, all in one command.
  • Migration files are plain, readable SQL, stored under prisma/migrations/, and can be reviewed like any other generated code.
  • Prisma tracks which migrations have already run in a _prisma_migrations table, so re-running the command is always safe.

Next lesson: changing a model and running a second migration, evolving a schema that’s already been applied.