First of all, what is Prisma and why do we need it?
Prisma is an awesome libarary if you are like me, bad at write SQL queries and is used to other databases such as Dynamo. It provides a really similar way in querying your data and reduce the stress of debugging SQL queries. It has a clean and type-safe API for submitting database queries which returns plain old JavaScript objects.
In this article, I will be going through the following:
Set Up PostgreSQL on Mac
Installation
We will first set up postrgreSQL, if you already have your database, skip this section.
If you like the interactive way of installing, you can dowload the installer here. However, I found that downloading using this method makes it really hard to make customization as all the config files are initally locked and you will have to manually change access permision for all.
In this article, we will install using homebrew. You can find out more about other installation methods here.
Run the following command from your terminal.
brew install postgresql@16This will install PostgreSQL 16, expose it to Port:5432, as well as creating a default database with name postgres at the following location /opt/homebrew/var/postgresql@16.
To create a new database, you can use the follwoing command.
initdb --locale=C -E UTF-8 path_to_your_directoryThis will create a new database at path_to_your_directory with locale setting to C and encoding setting to UTF-8.
You can find out more about the argument you can pass into initdb here.
We will be using the default database created by brew initially in this artical.
Here are couple really useful commands .
- To start postgresql@16 now or restart at login:
brew services start postgresql@16 - To stop the service:
brew services stop postgresql@16 - To get the list of service you have:
brew services list - To connect to the server and enter SQL command:
psql postgres
DataBase Visualization
I have also installed DBeaver for database visualisation.
Let’s first create a new connection by click on the icon below.

This will take us to Select your database. Choose PostgreSQL and let’s configure our connection setting.


The basic schema for your database URL will be look like the following.
jdbc:postgresql://{Host}:{Port}/{Database}And in my case, this will be:
jdbc:postgresql://localhost:5432/postgresYou can find out the Username by running brew services list and it is the User.
Name Status User File
postgresql@16 started itsuki ~/Library/LaunchAgents/homebrew.mxcl.postgresql@16.plistAnd for the Password, you can leave it empty.
Choose Finish.
Double click on the database name on the left side panel and you will be able to connect to it. You should see the green check back under the elephant icon.

Having our PostgreSQL database set up, we can now moving onto creating and configuring our Next.js project and Prisma.
Set Up Next Js with Prisma
Create new project
First of all create a new next js project like following.
npx create-next-app db-prisma-demoHere is how our directory look like initially.
.
├── .git
├── .gitignore
├── .next
├── README.md
├── next-env.d.ts
├── next.config.js
├── node_modules
├── package-lock.json
├── package.json
├── public
├── src
└── tsconfig.jsonInitialize Prisma
Go to your project directory and install the following libraries.
npm install prisma @prisma/clientAfter the installation, we can then initialize Prisma with
npx prisma initThis command will
- create a new directory called
prismawith a new file calledschema.prismathat contains the Prisma schema, database connction variables and schema models. We will take a more detail look at it later. - creates the
.envfile in the root directory to which we will be adding the database connection URL.
Below is our new directory structure.
.
├── .env
├── .git
├── .gitignore
├── .next
├── README.md
├── next-env.d.ts
├── next.config.js
├── node_modules
├── package-lock.json
├── package.json
├── prisma
├── public
├── src
└── tsconfig.jsonConfigure Prisma for PostgreSQL
Connect to Database
We will first add our connection URL to our .env file. It is similar to the URL we used when setting up DBeaver with just couple extra things.
The basic schema for the Base URL will be look like the following.
postgres://{username}:{password}@{hostname}:{port}/{database-name}In addtion, you can also add Arguments to it. We will be adding schema to ours. If schema is not set, it will automatically set to the default, ie: public, but let’s just add it anyway. The URL scheme will become the following.
postgres://{username}:{password}@{Host}:{Port}/{DatabaseName}?schema={schemaName}Yes, you’re right! We have never set something called password. You can just use postgres and it will work fine.
In my case, the URL will be:
DATABASE_URL="postgresql://itsuki:postgres@localhost:5432/postgres?schema=public"I actually don’t have to change anything in my schema.prisma . The provider is default to postgresql, and url being set to the environment variable. If yours looks different, change it to the following.
// schema.prisma
generator client {
provider = "prisma-client-js"
}
datasource db {
provider = "postgresql"
url = env("DATABASE_URL")
}Defining the Database Schema
This section is only for those of you who have an empty database or wish to add new tables to your database.
If that’s not you go, ie: you already have your database created and not going to add any new table, you can simply run the following command to turn your database schema into a Prisma schema and head to the next session.
npx prisma db pullSuppose we want a (new) table storing User data in our database. Here is the model we will be adding to our schema.prisma.
model User {
id Int @id
name String
}The User model two columns.
- an
idcolumn of typeIntwhich is the primary key - a
namecolumn of typeString.
By the way if you don’t have any schema from the beginning, this will create a new schema with User table.
After defining the model, we can deploy it to our database using
npx prisma db pushYou can check your DBeaver and should observe something similar to the following with your User Table with defined columns showing up.

Let’s add couple rows to the column so that we can query on it later.
Double click on your User Table and select Data Tab at top. Right click anywhere on the Grid and choose Add row. I have add itsuki and itsuki2 as my user for demo purpose.

Use Prisma in Next.js
Generate Client
First of all, let’s generate a Prisma Client that is tailored to our models by running the following command.
npx prisma generateThis command is actually also invoked when we installed @prisma/client, and you might and should see the following already showing up at the top of your schema.prisma file. But let’s run it again since we have modified Prisma schema.
generator client {
provider = "prisma-client-js"
}Create Client Instance
It is actually a little bit tricky when creating client instance within NextJs.
If you simply do const prisma = new PrismaClient() as what the tutorial for Node.js suggest, you might get the following error or stay in the loading state forever (that’s me, I am not getting the actual error on my console though).
warn(prisma-client) There are already 10 instances of Prisma Client actively running.The problem is that in development environment, the command next run dev clears Node.js cache on run. This in turn initializes a new PrismaClient instance each time due to hot reloading that creates a connection to the database. This can quickly exhaust the database connections as each PrismaClient instance holds its own connection pool and you will get the following error. You can get more details about the issues here.
Here is the solution.
Let’s create a new lib folder under src and add prisma.ts to it.
// prisma.ts
import { PrismaClient } from '@prisma/client'
const prismaClientSingleton = () => {
return new PrismaClient()
}
type PrismaClientSingleton = ReturnType<typeof prismaClientSingleton>
const globalForPrisma = globalThis as unknown as {
prisma: PrismaClientSingleton | undefined
}
const prisma = globalForPrisma.prisma ?? prismaClientSingleton()
export default prisma
if (process.env.NODE_ENV !== 'production') globalForPrisma.prisma = prismaThe idea here is to instantiate a single instance PrismaClient and save it on the globalThis object.
We will check globalThis to see if anything is stored on it. If nothing is on the object, we will create a new PrismaClient; otherwise, we will just reuse the one stored.
We can now import the client when we need it and start querying database.
Query Database
There are couple ways to use Prisma to query database within Next Js.
- getStaticProps
- getServerSideProps
- API Routes
Let’s start with a simple example where we will list all the users we have in the database. To do that we will be using the findMany() api in the format of prisma.$modelName.findMany() .
To use it in getServerSideProps:
// index.tsx
import prisma from '../lib/prisma'
export const getServerSideProps = async () => {
const users = await prisma.User.findMany()
console.log(users)
return { props: { users } }
}getStaticProps will be pretty much the same so I will skip it and move onto API route.
// api/fetchUser.ts
import prisma from '../lib/prisma'
import type { NextApiRequest, NextApiResponse } from 'next'
export default function handler(req: NextApiRequest, res: NextApiResponse) {
const users = await prisma.User.findMany()
res.status(200).json({ users: users });
}There are many many more APIs provided by Prisma that really makes life working with relational database such as PostgreSQL so much easier so check out what you can do here.
Source : https://medium.com/@2018.itsuki/postgresql-with-next-js-and-prisma-44f66a05378a
No comments:
Post a Comment