prisma-class-generator 제작 및 배포기
개요 - NestJS와 Prisma의 궁합은 어떤가?


기존의 TypeORM에서 Prisma로 마이그레이션 하면서 걸렸던 점이 하나 있는데,
TypeORM 같은 경우는 entity class를 정의하기 때문에 이 class 혹은 field에 decorator를 추가하여 자연스럽게 NestJS랑 핏이 잘 맞게 됩니다.
반면에 Prisma는 기본적으로 schema.prisma에 정의된 모델을 single source of truth로 삼아 타입들을 생성하기 때문에 엔티티 클래스를 별도로 정의할 필요가 없습니다.
그렇기 때문에 NestJS, 특히 swagger 등을 사용할 때는 DTO, response등을 class로 각각 정의해야 할 필요성이 있을 수도 있습니다.
작업
처음 이러한 기능의 필요성을 느껴 리서치를 해보니 prismaClient에서 dmmf란 Object를 얻을 수 있는데 이를 이용하여 schema.prisma의 메타데이터를 파싱하여 클래스를 생성해주는 Function을 export하여 제공했습니다.
import { PrismaClient } from '@prisma/client'
import { DMMFClass } from '@prisma/client/runtime'
import { writeFromDMMF } from 'prisma-class-generator'
// @ts-ignore
const dmmf: DMMFClass = new PrismaClient()._dmmf
writeFromDMMF({
dmmf: dmmf as any,
outputType: 'file',
targetDir: <PATH DIRECTORY TO WRITE RESULT CLASSES>,
useSwagger: true,
})
추후 슬랙에서 비슷한 라이브러리를 보니 이런 방식이 아닌 추가적인 generator를 배포하는 방식이었습니다. 사실 공식문서에서 커스텀 generator를 사용할 수 있게 제공했는데 제가 이 부분을 체크하지 못하였기 때문에 이러한 방식으로 작업한 것이었습니다.
다행히 더 좋은 방식 및 인사이트를 얻었으니 이 방식으로 전면 리팩토링했습니다.
GitHub - kimjbstar/prisma-class-generator: Class generator from Prisma schema

고민사항
어느정도 기본적인 기능은 만들었다 싶어 홍보를 위해 prisma 공식 slack을 체크해 보았는데 #nest-generator라는 채널이 이미 있었고, 비슷한 기능을 하는 라이브러리가 두어개 정도 존재했습니다.

그래서 든 고민은, 이미 이러한 라이브러리들이 있는데 제가 추가하여 비슷한 기능을 가진 라이브러리를 파편화 시키는 것 아닌가? 라는 것이었습니다. 그래서 이 라이브러리 개발에 합류하여 같이 고도화시키는게 어떤가 라는 생각도 했습니다.
하지만 고민해본 결과 그럴 정도로 다른 라이브러리들이 고도화되어 있지 않았고, 제 플랜에는 오히려 기존에 파편화된 라이브러리 기능들을 통합할 계획도 있기 때문에 기존 방향대로 진행하기로 마음 먹었습니다.
커뮤니티, 슬랙 등 기존 존재하는 generator 프로젝트들 리서치
class, DTO 관련
- prisma-generator-nestjs-dto
- prisma-nestjs-dto-generator
graphQL 관련
- typegraphql-prisma
- prisma-nestjs-graphql
-> prisma-class-generator는 이 모두를 통합하여 지원하는 것이 최종 목표!
배포
우선 한글로 되어 있는 README.md를 전부 영어로 교체하고, 소개 및 예제를 추가했습니다.
만약 이 라이브러리를 홍보한다면 생각할 수 있는 채널은 이정도가 있다고 정리했습니다.
- Nestjs 오픈채팅방
- prisma slack
- NestJS discord
- prisma doc
공식 문서에 추가 - prisma doc에 PR
위 generator 문서를 보면 community generator(비공식) 목록이 있는데, 제 라이브러리를 여기에 올리고 싶었습니다. 처음에는 슬랙 등 커뮤니티를 통해 코어 컨트리뷰터 등한테 어필(?)을 하여 추가되는 줄 알았는데, prisma 문서 프로젝트에 직접 PR을 보내 반영되는 방식이었습니다. 코드리뷰와 프로젝트 체크도 이 때 진행되는 것으로 보입니다.
과정
- 우선 프로젝트를 fork받아 해당 페이지를 수정 후 PR 요청을 해보았습니다. 생각보다 빠르게 코드리뷰가 진행되었고, edit suggestion이 담긴 답글이 달려, 수정 반영 후 기다리자 곧 merge가 되었습니다.
add prisma-class-generator to community generators by kimjbstar · Pull Request #2390 · prisma/docs


- 또한 제 라이브러리의 README.md 수정 PR도 요청해주셔서 바로 반영했습니다. 😄


docs(README): Small fixes by janpio · Pull Request #1 · kimjbstar/prisma-class-generator
결론
-
sequelize-typescript-migration을 만들었을 때는 소위 홍보도 하지 않고 방치시켰다면, 이번 같은 경우 여러 채널을 통해 홍보 예정이고 Prisma 프로젝트 자체도 개발이 활발하게 이루어지기 때문에 소위 보는 눈(?)이 더 많을 것으로 보입니다. 그렇기 때문에 더 책임감을 느끼고 개발해야 한다는 마음가짐이 더 큽니다.
-
Pull Request가 README.md 쪽이 아닌 로직 수정 관련하여 요청이 들어올 수도 있으니 테스트 및 배포 자동화의 우선순위도 높을 것으로 보입니다.
-
마지막으로 영어 공부의 필요성을 많이 느꼈습니다. PR을 보냈을때는 리뷰가 빠르고 반영이 빨라 놀라웠지만, 동시에 부끄러움도 느꼈습니다. 코드 쪽에만 신경썼지 README 및 가이드 쪽 영어에는 신경을 크게 쓰지 못해 오탈자 및 영어 문법쪽에서 수정 소요가 추가로 있었기 때문입니다. 앞으로 오픈소스 등을 작업하면 영어로 소통하는 것이 기본일텐데, 더욱 영어와 친숙해지도록 노력을 해야 할 것으로 보입니다.
정리
이 글은 generator를 만들었다는 결과보다, 오픈소스 작업에서 코드 바깥의 품질이 얼마나 중요한지 배운 기록에 가깝습니다.
처음에는 Prisma 내부의 DMMF를 직접 읽는 방식으로 시작했지만, 나중에 공식 generator 구조를 보고 방향을 바꿨습니다. 라이브러리를 만들 때는 기능을 빨리 구현하는 것만큼, 그 생태계가 권장하는 확장 지점을 먼저 찾는 일이 중요했습니다.
또 문서 PR을 보내면서 README, 예제, 영어 표현이 라이브러리의 일부라는 걸 체감했습니다. 코드는 동작해도 설명이 어색하면 사용자는 설치까지 가지 못합니다. 특히 generator처럼 프로젝트 설정에 들어가는 도구는 “무엇을 생성하고, 어디에 쓰이며, 기존 코드에 어떤 영향을 주는지”가 문서에서 먼저 보여야 했습니다.
용어 짧게 정리
- generator: Prisma schema를 읽어 필요한 파일이나 타입을 자동 생성하는 확장 도구입니다.
- DMMF: Prisma schema를 파싱해 얻는 내부 메타데이터 구조입니다.
- DTO: API 요청과 응답 형태를 표현하는 객체입니다.
- Swagger: API 스펙과 문서를 생성하고 확인하는 도구입니다.
- community generator: Prisma 공식 기능은 아니지만 커뮤니티에서 만든 generator입니다.
- README: 라이브러리를 처음 만난 사용자가 설치와 사용법을 확인하는 문서입니다.