지난 포스팅에 이어 이번에는 prisma
를 사용하여 database를 연동해보도록 한다.
SQLite
를 DB로 이용하여 데이터를 저장할 예정이다.
본 시리즈는 HOW TO GRAPHQL 글을 참고하여 작성했습니다.
기존에 참조하던 cadenzah 님의 포스팅이 deprecated되어 새롭게 작성하였습니다.
오타 및 의역이 있을 수 있으니 양해를 부탁 드리며, 수정 사항은 댓글로 알려주세요.
기존에 Prisma1에서
Prisma2
로 변경되며 많은 부분이 변경되었다. 이로 인해, GraphQL 블로그의 튜토리얼이 변경된듯 하다.
내가 이 시리즈의 포스팅을 작성하게 된 가장 큰 이유가 된 부분이다..
Prisma
는 개발자들이 깔끔
하고 type-safe
한 API를 통해 데이터베이스에 접근하게 해주는 오픈소스
이다.
이는 다음과 같은 3가지 툴과 각각의 기능으로 구성이 되어있다.
Primsa Client
: Node.js 및 TypeScript를 위한 쿼리 자동 생성Prisma Migrate
: 명시적인 데이터 모델링 및 마이그레이션 시스템Prisma Studio
: GUI를 통한 데이터베이스 접근 및 수정 지금까지 살펴본 방법으로 매우 간단하고 아름답게 GraphQL 서버가 동작함을 알 수 있다.
그러나 실제로 서버를 개발할 때는 이렇게 간단한 문제들로만 구성되는 않는다.
특히 GraphQL 쿼리들은 깊은 단계로 중첩
이 될 수 있는데, 이때 리졸버를 구현하는 것은 까다롭고
, 성능문제
를 야기할 수 있다.
이러한 개발자들의 고충을 해결하기 위해, Prisma는 더욱 효율적으로 데이터에 접근하는 방법에 초점을 맞췄다.
우선 다음의 명령을 통해 Prisma CLI
를 설치한다.
# ./hackernews-node/
npm install @prisma/cli --save-dev
다음의 명령을 통해 schema.prisma
파일을 생성한다.
# ./hackernews-node/
mkdir prisma
touch prisma/schema.prisma
Prisma1과 Prisma2가 가장 다른 점은 위의 방법처럼 Database에 관련된
파일
을 관리하는 방법과아키텍처
가 다르다.
자세한 사항은 Prisma2와 Prisma1의 차이점을 참고
위의 과정을 통해 생성된 schema.prisma
는 데이터베이스 스키마처럼 생각하면 되며, 다음과 같이 구성된다.
Data source
: 데이터베이스에 연결한다.Generator
: Prisma Client를 생성한다.Data model
: 애플리케이션의 모델을 정의한다.이를 코드로 작성해보자.
// ./hackernews-node/prisma/schema.prisma
// 1
datasource db {
provider = "sqlite"
url = "file:./dev.db"
}
// 2
generator client {
provider = "prisma-client-js"
}
// 3
model Link {
id Int @id @default(autoincrement())
createdAt DateTime @default(now())
description String
url String
}
Link
모델은 link
데이터 베이스 테이블의 구조를 정의하며, Prisma는 이를 기반으로 테이블을 생성해준다.
드디어 SQLite
데이터베이스를 만들 시간이다. SQLite는 serverless
, 설정의 간편함
, 트랜잭션
등 다양한 장점이 있다.
또한 다른 SQL 데이터베이스와는 달리 별도의 서버 프로세스가 없어 일반 디스크 파일에 직접 읽고 쓰기를 수앻한다.
하나의 완전한 데이터 베이스(table, indice, trigger 및 view)가 하나의 디스크 파일에 포함된다.
이러한 장점은 본 프로젝트와 잘 어울린다.
다행히 Prisma와의 연동은 간편하게 진행할 수 있는데, 다음과 같은 명령어를 통해 migration
을 생성함으로써 가능하다.
# ./hackernews-node/
npx prisma migrate save --experimental
위의 명령어를 수행하면 다음과같이 묻는 문구가 뜨게 되는데 Yes를 클릭하고, 이름을 정해준다.
You are trying to create a migration for SQLite database dev.db.
A database with that name doesn't exist at file:./dev.db
> YES
> Name of migration:
성공적으로 수행하고 나면, prisma
디렉토리 밑에 /migrations
라는 디렉토리가 생성되었음을 알 수 있다.
README.md
파일을 참조하면, 우리가 생성한 Link
에 대한 테이블구성을 볼 수 있으며, 여러가지 수정사항이 함께 기록된다.
이제 실제로 데이터베이스에 대해 마이그레이션
을 실행하기 위해 다음의 명령을 수행한다.
# ./hackernews-node/
npx prisma migrate up --experimental
이제 테이블이 있는 데이터베이스가
생성
되었다.
위에서 생성한 데이터 모델을 기반으로 Prisma Client를 생성해보자.
# ./hackernews-node/
npx prisma generate
성공적으로 수행된다면, Prisma client를 /node_modules/@prisma/client
에서 가져와 사용할 수 있다는 문구가 뜨게 된다.
Prisma Client로 첫 번째 쿼리를 만들어서 분석을 하기 위해, 별도의 src/script.js
파일을 만들고 다음 코드를 추가한다.
// 1
const { PrismaClient } = require("@prisma/client")
// 2
const prisma = new PrismaClient()
//3
async function main() {
const allLinks = await prisma.link.findMany()
console.log(allLinks)
}
//4
main()
.catch(e => {
throw e
})
// 5
.finally(async () => {
await prisma.$disconnect()
})
위 코드는 다음과 같이 동작한다.
PrismaClient
에서 생성자를 가져옴PrismaClient
async
로 호출되는 main 함수를 정의위와 같이 정상적으로 설정된다면, 아래 사진처럼 자동완성이 가능해진다.
위에서 작성한 스크립트를 다음의 명령으로 실행하자.
# ./hackernews-node/
node src/script.js
성공적으로 수행된다면, 아무것도 없는 빈배열
이 응답될 것이다. 새로운 link 생성을 위해 다음과 같이 추가한다.
// ./hackernews-node/src/script.js
...
async function main() {
const newLink = await prisma.link.create({
data: {
description: 'Fullstack tutorial for GraphQL',
url: 'www.howtographql.com',
},
})
const allLinks = await prisma.link.findMany()
console.log(allLinks)
}
다음과 같이 성공적으로 가져온 결과물을 확인할 수 있다.
[ { id: 1,
createdAt: 2020-11-17T07:33:26.767Z,
description: 'Fullstack tutorial for GraphQL',
url: 'www.howtographql.com' } ]
데이터를 업데이트하는 위의 과정들을 요약하자면 다음과 같다.
prisma migrate
명령을 통해 데이터베이스 마이그레이션Prisma Client
생성Prisma와 SQLite를 이용하여 데이터베이스에 데이터를 저장하는 방법에 대해 알아보았다.
다른 DB를 사용하기 위해서는 datasource에 다른 db를 연결하면 된다.
Prisma는 꼭 GraphQL이 아니라 REST
ful API에서도 사용이 가능하다.
이곳을 참조
다음 포스팅에서는 리졸버 함수 내에서 데이터베이스에 접근하는 방법에 대해 알아보도록 한다.