apps/docs/content/docs/(index)/prisma-orm/quickstart/planetscale.mdx
PlanetScale is a serverless database platform. This guide covers both PlanetScale MySQL and PlanetScale Postgres. In this guide, you will learn how to set up a new TypeScript project from scratch, connect it to PlanetScale using Prisma ORM, and generate a Prisma Client for easy, type-safe access to your database.
You also need:
mkdir hello-prisma
cd hello-prisma
Initialize a TypeScript project:
npm init -y
npm install typescript tsx @types/node --save-dev
npx tsc --init
Install the packages needed for this quickstart:
npm install prisma --save-dev
npm install @prisma/client @prisma/adapter-planetscale undici dotenv
npm install prisma @types/pg --save-dev
npm install @prisma/client @prisma/adapter-pg pg dotenv
Update tsconfig.json for ESM compatibility:
{
"compilerOptions": {
"module": "ESNext",
"moduleResolution": "bundler",
"target": "ES2023",
"strict": true,
"esModuleInterop": true,
"ignoreDeprecations": "6.0"
}
}
Update package.json to enable ESM:
{
"type": "module" // [!code ++]
}
You can now invoke the Prisma CLI by prefixing it with npx:
npx prisma
Next, set up your Prisma ORM project by creating your Prisma Schema file with the following command:
npx prisma init --datasource-provider mysql --output ../generated/prisma
npx prisma init --datasource-provider postgresql --output ../generated/prisma
This command does a few things:
prisma/ directory with a schema.prisma file containing your database connection and schema models.env file in the root directory for environment variablesprisma.config.ts file for Prisma configurationThe generated prisma.config.ts file looks like this:
import "dotenv/config";
import { defineConfig, env } from "prisma/config";
export default defineConfig({
schema: "prisma/schema.prisma",
migrations: {
path: "prisma/migrations",
},
datasource: {
url: env("DATABASE_URL"),
},
});
The generated schema uses the ESM-first prisma-client generator with a custom output path:
generator client {
provider = "prisma-client"
output = "../generated/prisma"
}
datasource db {
provider = "mysql"
relationMode = "prisma"
}
generator client {
provider = "prisma-client"
output = "../generated/prisma"
}
datasource db {
provider = "postgresql"
}
:::info
PlanetScale MySQL requires relationMode = "prisma" because it doesn't support foreign key constraints.
:::
Update your .env file with your PlanetScale connection string:
DATABASE_URL="mysql://username:[email protected]/mydb?sslaccept=strict"
DATABASE_URL="postgresql://{username}:{password}@{host}:6432/postgres?sslmode=verify-full"
Replace with your actual PlanetScale credentials from your database dashboard.
:::note
PlanetScale Postgres connection types:
| Type | Port | Use case |
|---|---|---|
| Direct | 5432 | Prisma CLI commands (migrations, introspection), Prisma Studio |
| PgBouncer | 6432 | Application connections, serverless environments |
For production applications, we recommend using PgBouncer (port 6432) for application connections while keeping a direct connection for Prisma CLI commands.
:::
Open prisma/schema.prisma and add the following models:
generator client {
provider = "prisma-client"
output = "../generated/prisma"
}
datasource db {
provider = "mysql"
relationMode = "prisma"
}
model User { // [!code ++]
id Int @id @default(autoincrement()) // [!code ++]
email String @unique // [!code ++]
name String? // [!code ++]
posts Post[] // [!code ++]
} // [!code ++]
model Post { // [!code ++]
id Int @id @default(autoincrement()) // [!code ++]
title String // [!code ++]
content String? @db.Text // [!code ++]
published Boolean @default(false) // [!code ++]
author User @relation(fields: [authorId], references: [id]) // [!code ++]
authorId Int // [!code ++]
@@index([authorId]) // [!code ++]
} // [!code ++]
generator client {
provider = "prisma-client"
output = "../generated/prisma"
}
datasource db {
provider = "postgresql"
}
model User { // [!code ++]
id Int @id @default(autoincrement()) // [!code ++]
email String @unique // [!code ++]
name String? // [!code ++]
posts Post[] // [!code ++]
} // [!code ++]
model Post { // [!code ++]
id Int @id @default(autoincrement()) // [!code ++]
title String // [!code ++]
content String? // [!code ++]
published Boolean @default(false) // [!code ++]
author User @relation(fields: [authorId], references: [id]) // [!code ++]
authorId Int // [!code ++]
} // [!code ++]
:::note
Note the @@index([authorId]) on the Post model for MySQL. PlanetScale MySQL requires indexes on foreign keys when using relationMode = "prisma".
:::
npx prisma db push
npx prisma migrate dev --name init
This command creates the database tables based on your schema.
Now run the following command to generate the Prisma Client:
npx prisma generate
:::note
PlanetScale MySQL uses a branching workflow instead of traditional migrations, so we use prisma db push. PlanetScale Postgres supports standard migrations with prisma migrate dev.
:::
Now that you have all the dependencies installed, you can instantiate Prisma Client. You need to pass an instance of the Prisma ORM driver adapter adapter to the PrismaClient constructor:
import "dotenv/config";
import { PrismaPlanetScale } from "@prisma/adapter-planetscale";
import { PrismaClient } from "../generated/prisma/client";
import { fetch as undiciFetch } from "undici";
const adapter = new PrismaPlanetScale({ url: process.env.DATABASE_URL, fetch: undiciFetch });
const prisma = new PrismaClient({ adapter });
export { prisma };
import "dotenv/config";
import { PrismaPg } from "@prisma/adapter-pg";
import { PrismaClient } from '../generated/prisma/client'
const connectionString = `${process.env.DATABASE_URL}`;
const adapter = new PrismaPg({ connectionString });
const prisma = new PrismaClient({ adapter });
export { prisma };
Create a script.ts file to test your setup:
import { prisma } from "./lib/prisma";
async function main() {
// Create a new user with a post
const user = await prisma.user.create({
data: {
name: "Alice",
email: "[email protected]",
posts: {
create: {
title: "Hello World",
content: "This is my first post!",
published: true,
},
},
},
include: {
posts: true,
},
});
console.log("Created user:", user);
// Fetch all users with their posts
const allUsers = await prisma.user.findMany({
include: {
posts: true,
},
});
console.log("All users:", JSON.stringify(allUsers, null, 2));
}
main()
.then(async () => {
await prisma.$disconnect();
})
.catch(async (e) => {
console.error(e);
await prisma.$disconnect();
process.exit(1);
});
Run the script:
npx tsx script.ts
You should see the created user and all users printed to the console!
Prisma Studio is a visual editor for your database. Launch it with:
npx prisma studio
You've successfully set up Prisma ORM. Here's what you can explore next: