Prisma 란?
prisma는 Node.js와 TypeScript ORM이다.
ORM은 Object Relational Mapping이라는 뜻이고 기본적으로 번역기의 역할을 한다고 생각하면된다.
JavaScript 혹은 TypeScript 코드와 DB사이에 다리를 놓아준다.
(mongo DB의 Mongoose를 떠올리면 쉬울것 같다.)
Prisma를 사용하기전에 데이터베이스가 어떻게 생겼는지를 schema.prisma라는 파일에 설명해줘야한다.
예를 들면 아래와 같다.
// This is your Prisma schema file,
// learn more about it in the docs: https://pris.ly/d/prisma-schema
generator client {
provider = "prisma-client-js"
}
datasource db {
provider = "mysql"
url = env("DATABASE_URL")
relationMode = "prisma"
}
model User {
id Int @id @default(autoincrement())
name String
phone Int? @unique
email String? @unique
avatar String?
createAt DateTime @default(now())
updatedAt DateTime @updatedAt
}
이러한 타입에 관한 정보를 알고 있으면, Clinet를 생성해 줄 수 있다.
Client를 이용하면 타입스크립트로 데이터베이스와 직접 상호작용할 수 있다.
prisma에게 DB가 어떻게 생겼느지 설명해주면 Prisma는 Client를 생성해 줄 거고 그 Client 안에 필요한 모든 name이 들어있을 것이다.
더불어 Prisma Studio라는 Visual Database Browser있는데 이것은 데이터베이스를 위한 관리자 패널(Admin panel) 같은 것이다.
데이터베이스는 PostgreSQL / MySQL / SQL Server / SQLite / MongoDB에 사용할 수 있다.
Prisma Setup
1. VSCode에서 PRISMA EXTENTIONS찾아서 설치
2. Prisma 설치
npm i prisma -D
3. 설치 후 Prisma 불러오기 (Prisma를 사용할 때면 항상 npx prisma 라는 명령어 사용)
npx prisma init
위 코드를 입력시 application 안에 prisma 폴더가 생겼고 .env 파일도 생성이됨
생성 후에 VSCode 터미널에 다음으로 해야할 사항들이 나열되어있는데
- .env파일에 있는 DATABASE_URL을 설정해줘야함 . 초기설정에 postgresql이 설정되어 있는데 자신이 사용하는 DB URL을 기입
- schema.prisma 파일에서 datasource의 provider를 설정 해야함
// This is your Prisma schema file,
datasource db {
//provider는 우리가 사용할 데이터베이스를 말한다.
provider = "mysql"
url = env("DATABASE_URL")
relationMode = "prisma"
}
//사용할 user에 대한 schema를 만들어준다. 만들때 model이라고 작성 후 이름을 붙어주고 사항들을 붙어준다.
model User {
id Int @id @default(autoincrement())
//@id는 모델의 id라는 걸 알려주는 역할을 하며 유니크한 식별자이다.
//@default로 기본값을 지정해주는데 autoincrement로 자동으로 증가하는 field로 설정함.
name String
phone Int? @unique
//?의 표시는 값이 들어올수도 아닐수도 있다는 표시이며 @unique라는 걸 붙이게 되면 값이 중복될수가 없다.
email String? @unique
avatar String?
createAt DateTime @default(now())
//user가 만들어지고 난 시점(now())을 넣어준다.
updatedAt DateTime @updatedAt
// @updateAt은 유저가 업데이트 될 때마다 이 field값이 변할 거라고 prisma에게 알려줄거다.
}
PlanetScale
(이하 pscale)
pscale은 MySQL과 호환되는 Serverless 데이터베이스 플랫폼이다.
이 말은 즉슨, 데이터베이스를 제공해주며 , serverless는 정말로 서버가 없다는 것이 아니라 , 서버를 우리가 유지보수할 필요가 없다는 뜻이다.
예를 들어 백만명이 작업자의 데이터베이스에 연결되면 직접 scaling(확장)시켜줘야하는데 이런 플랫폼을 사용하면 그런 작업을 대신 해준다.
vitess - pscale에 따르면 가장 scaling 기능이 뛰어난 오픈 소스데이터베이스이다. vitess는 유튜브를 scale하기 위해 구글이 만든 것.
vitess는 대기업들이 규모에 맞게 MySQL을 scale하기 위해 쓰는 방법이다.
pscale은 CLI가 있다. CLI로 데이터베이스를 다룰 수 있다. 어떠한 Model을 수정한다면 모두가 사용하는 메인 데이터베이스를 직접 수정하는 대신 데이터베이스에 brach를 만들수가 있다. 그 brach에서 schema도 바꾸고 새로 model도 만들고 field도 수정할 수 있다. 수정 후에는 schema를 옮기는 건데 그걸 알아서 합쳐줄것이다.
PlanetScale Connecting
**pscale을 연결하기 위해서는 일단 회원가입을하고 카드를 등록해줘야 원할히 연결할 수 있다.
1 . CLI를 사용을 위해 터미널에 명령어를 입력해준다. (mac 사용자)
brew install planetscale/tap/pscale
brew install mysql-client
window 유저라면 scoop을 통해 다운로드 (scoop은 콘솔을 통해서 쉽게 다운로드 받게 해줄수 있는 도구 https://scoop.sh)
설치가 완료됬다면 VSCode 터미널에서 pscale를 입력하면 그와 관련된 명령어들이 나온다.
2. 설치 후에는 pscale auth login 을 통해 로그인 해준다. 이때 카드 등록은 필수이며 vscode의 터미널에 나오는 숫자와 브라우저에 나오는 숫자를 잘 대조한다.
3. vscode로 다시 돌아와서 pscale region list를 터미널에 작성하면 slug의 태그 이름을 복사해서
pscale database create 프로젝트이름 --region "region slug"
이러면 데이터베이스가 만들어질것이다.
4. pscale의 관리자 패널로 가보면 만들어져 있는 것을 볼 수 있을 것이다. (브라우저에서 로그인 후 확인)
브라우저에서도 데이터베이스를 만들 수 있다.
5. prisma와 연결하기 위해 .env에 있는 DATABASE_URL를 바꿔줘야하는데 보통 데이터베이스 플랫폼에서는 데이터베이스를 하난 만들면 암호를 생성해야한다. 암호를 환경파일에 집어넣어야한다. 이렇게 되면 내 장치에 암호가 저장되는 꼴이 되어서 보안에 취약할 수 있다.
따라서 사람들이 보통하는 방식은 컴퓨터로 작업할 때 직접 진짜 데이터베이스를 건들지 않고 가짜와 진짜로 두 개의 데이터베이스를 운영한다.
대신에 pscalse에서는 일종의 보안 tunnel을 이용할 수 있다. 컴퓨터와 pscale 사이에 암호를 알 필요가 없어진다.
pscale 보안연결을 하기 위해서는 CLI를 활용해야한다.
pscale connect 데이터베이스이름
이렇게 작성하면 터미널에 URL이 나온다.
Local address to connect your application: 127.0.0.1:3306 (press ctrl-c to quit)
콘솔을 절대 종료하지 않고 URL을 복사하여 env파일에 작성해준다.
DATABASE_URL="데이터베이스관리시스템이름://콘솔창에 나온 URL/프로젝트명"
이렇게 하면 pscalse와 연결이 되었다.
6. 연결 후 해야하는게 있는데 MySQL은 하는데 vitess는 하지 않는 몇가지가 있는데 그중에 foreign key 제약이다.
/*
foreign key는 예를 들어
User DB: [
{id:1 , userName :"hoho"}
]
게시판 DB:[
{게시물의 id:1 , text:"hahahoho", 작성자: userID(1)}
]
이렇게 되면 게시판의 게시글의 작성자가 누가 누군지 알게 된다.
이러한 방식을 foreign key라고 한다.
MySQL이나 postgreSQL은 이러한 방식을 사용하지만 vitess는 이러한 방식을 사용하지 못한다.
만약 게시물의 작성자 id가 5가 되었다면 작동되지 않았겠지만 pscale에서는 아무 문제 없이 작동이 된다.
이게 작동되는 이유는 MySQL과 vitess의 차이점 때문이다.
vitess는 Scalability에 특화되어 있다.
vitess는 데이터베이스를 잘게 쪼개서 여러 서번에 분산시키는데에 특화되어 있다.
vitess는 게시물을 생성하기 전에 사요자가 존재의 유무를 확인하지 않는다.
그래서 보통은 데이터베이스에게 도움을 받아 존재의 유무를 확인한다. 하지만 우리는 prisma를 사용해 도움을 받을 수 있다.
*/
//schema.prisma
//... 기존 코드들
datasource db {
provider = "mysql"
url = env("DATABASE_URL")
// 아래 코드 추가
relationMode = "prisma"
}
코드 추가 후에 VSCode 콘솔 창에 작성
npx prisma db push
후에 pscale의 해당 데이터베이스 Brach로가면 schema.prisma에서 작성한 모델이 올라가있는것을 볼 수 있다.
npx prisma studio
위의 명령어를 입력하게 되면 데이터 베이스 관리자 패널을 볼 수 있다.
Prisma Client
prisma가 prisma client라는걸 제공해준다.
npm i @prisma/client
typescript 파일을 만들고
import {PrismaClient} from "@prisma/client";
export default new PrismaClient();
npx prisma generate
client를 생성했다는 메세지를 볼 수 있다.
prisma client는 브라우저에서 실행할 수 없다. 프론트 단에서 실행할 수 없다.
DB에 접근하는 것은 프론트단에 작성하면 안된다.
API ROUTES (next.js)
prisma client를 접근하기 위해 서버, 즉 백엔드 코드를 작성할 곳이 필요하다.
보통같으면 백엔드로 nodejs를 사용해서 백엔드 코드를 작성할텐데 NextJS는 API를 만들기 위해 다른 서버를 구축할 필요가 없을 정도로 좋다.
app 폴더에 api 폴더를 만들고 route.ts를 만든다. 이렇게 만들면 api서버가 완성된다.
import {NextResponse} from "next/server";
import client from "../../../../util/client";
//Next JS에서 req,res object를 제공하는데 TS사용한다면 다음과 같이 지정
export async function GET() {
await client.user.create({
data: {
name: "hahah",
email: "11@22.22",
},
});
return NextResponse.json({
ok: true,
data: "xxx",
});
}
이후 Prisma studio에 들어와서 확인하면 유저가 생성된걸 볼 수 있다. 이때 prisma와 pscale은 계속 연결이 되어야 한다.