[ ๋ฌด๋ฌผ ] Prisma ORM ์œผ๋กœ NextJS ๋ฐฑ์—”๋“œ ์„œ๋ฒ„ ๊ตฌ์ถ•ํ•˜๊ธฐ

2025. 10. 21. 00:42ยท๐Ÿงก Projects/๐Ÿงก Projects: Web
728x90

 

 ๐Ÿ™์„ฑํ–ฅํ…Œ์ŠคํŠธ ๊ธฐ๋ฐ˜ AI ์š”๊ธˆ์ œ ์ถ”์ฒœ ์„œ๋น„์Šค , ๋ฌด๋ฌผ ๋ฐ”๋กœ๊ฐ€๊ธฐ๐Ÿ™

 

moo-mool

[LG U+ ์œ ๋ ˆ์นด 2๊ธฐ] ํ”„๋ก ํŠธ์—”๋“œ ์ข…ํ•ฉํ”„๋กœ์ ํŠธ 1์กฐ (UgodIT). moo-mool has 4 repositories available. Follow their code on GitHub.

github.com

๋“ค์–ด๊ฐ€๋ฉฐ

ํ”„๋กœ์ ํŠธ๋ฅผ ์‹œ์ž‘ํ•  ๋•Œ ์›๋ž˜ ๊ตฌ์ƒ์€ ๋ฐฑ์—”๋“œ๋Š” Java Spring, ํ”„๋ก ํŠธ์—”๋“œ๋Š” Next.js๋กœ ๋ถ„๋ฆฌํ•˜๋Š” ๋ฐฉ์‹์ด์—ˆ์Šต๋‹ˆ๋‹ค. ํ•˜์ง€๋งŒ ์ €ํฌ ํŒ€์€ ๋ชจ๋‘ ํ”„๋ก ํŠธ์—”๋“œ ๊ฐœ๋ฐœ์ž๋กœ, Java๋ณด๋‹ค๋Š” TypeScript ํ™˜๊ฒฝ์— ํ›จ์”ฌ ์ต์ˆ™ํ–ˆ์Šต๋‹ˆ๋‹ค. ๋˜, ์ด๋ฒˆ ํ”„๋กœ์ ํŠธ๋Š” AI๋ฅผ ํ™œ์šฉํ•ด์•ผ ํ•˜๋Š” ๋ช…ํ™•ํ•œ ์š”๊ตฌ์‚ฌํ•ญ์ด ์žˆ์—ˆ๊ธฐ ๋•Œ๋ฌธ์— ๋ฐฑ์—”๋“œ์˜ ๊ณ ๋„ํ™”๋ณด๋‹ค ํ”„๋ก ํŠธ์—”๋“œ ์™„์„ฑ๋„์™€ ์‚ฌ์šฉ์ž ๊ฒฝํ—˜์„ ๋” ์ค‘์š”ํ•œ ๋ชฉํ‘œ๋กœ ๋‘์—ˆ์Šต๋‹ˆ๋‹ค. ์ž์—ฐ์Šค๋Ÿฝ๊ฒŒ ๊ฐœ๋ฐœ ๋ฆฌ์†Œ์Šค๋ฅผ ์ตœ์†Œํ™”ํ•  ์ˆ˜ ์žˆ๋Š” ๋ฐฉํ–ฅ์„ ์ฐพ๊ฒŒ ๋˜์—ˆ์Šต๋‹ˆ๋‹ค.
๊ทธ๋Ÿฌ๋˜ ์ค‘ Next.js์˜ API Routes ๊ธฐ๋Šฅ์„ ํ™œ์šฉํ•˜๋ฉด Node.js ๊ธฐ๋ฐ˜์œผ๋กœ ํ•„์š”ํ•œ ์ˆ˜์ค€์˜ ๋ฐฑ์—”๋“œ API๋ฅผ ์ง์ ‘ ์ž‘์„ฑํ•  ์ˆ˜ ์žˆ๊ณ , Prisma ORM์„ ํ†ตํ•ด MYSQL ์—ฐ๋™๊นŒ์ง€ ๊ฐ€๋Šฅํ•˜๋‹ค๋Š” ์ ์„ ํ™•์ธํ–ˆ์Šต๋‹ˆ๋‹ค. ์ฆ‰, NextJS ํ•˜๋‚˜๋กœ FE์™€ BE๋ฅผ ๋ชจ๋‘ ์ปค๋ฒ„ํ•  ์ˆ˜ ์žˆ์—ˆ์Šต๋‹ˆ๋‹ค


NextAuth ์‚ฌ์šฉํ•œ ์ด์œ 

๊ฐ€์žฅ ๋จผ์ € ํ•ด๊ฒฐํ•ด์•ผ ํ–ˆ๋˜ ๊ณผ์ œ๊ฐ€ ์นด์นด์˜ค ๋กœ๊ทธ์ธ์„ ํฌํ•จํ•œ ์ธ์ฆ์ด์—ˆ์Šต๋‹ˆ๋‹ค. ์ธ์ฆ์€ ์ง์ ‘ ๊ตฌํ˜„ํ•  ์ˆ˜๋„ ์žˆ์ง€๋งŒ, OAuth ํ”„๋กœํ† ์ฝœ ์ฒ˜๋ฆฌ, ํ† ํฐ ์žฌ๋ฐœ๊ธ‰, ์„ธ์…˜ ๊ด€๋ฆฌ๊นŒ์ง€ ์ „๋ถ€ ์‹ ๊ฒฝ ์“ฐ๋Š” ๊ฑด ๋ฆฌ์Šคํฌ์™€ ๋น„์šฉ์ด ์ปธ์Šต๋‹ˆ๋‹ค. ํŒ€ ๋ฆฌ์†Œ์Šค๋ฅผ ๊ณ ๋ คํ–ˆ์„ ๋•Œ, ๋ณด์•ˆ ๋กœ์ง์„ ์ง์ ‘ ์งœ๊ธฐ๋ณด๋‹ค๋Š” ๊ฒ€์ฆ๋œ ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ๋ฅผ ๋„์ž…ํ•ด ๊ฐœ๋ฐœ ์†๋„๋ฅผ ๋†’์ด๊ณ  ์•ˆ์ •์„ฑ์„ ํ™•๋ณดํ•˜๋Š” ๊ฒŒ ๋” ํ•ฉ๋ฆฌ์ ์ด์—ˆ์Šต๋‹ˆ๋‹ค.

 

 

1. ์นด์นด์˜ค OAuth Provider ์ง€์›

// ์นด์นด์˜ค OAuth ์„ค์ • - ์ปค์Šคํ…€ ๊ตฌํ˜„ ์—†์ด ๋ฐ”๋กœ ์ ์šฉ
import KakaoProvider from "next-auth/providers/kakao"

๋ณ„๋„ ์ปค์Šคํ…€ ์—†์ด KakaoProvider๋ฅผ ๋ถˆ๋Ÿฌ์™€ ๋ฐ”๋กœ ์ ์šฉ ๊ฐ€๋Šฅํ•ด ์ดˆ๊ธฐ ๊ตฌ์ถ• ์†๋„๋ฅผ ๋‹จ์ถ•ํ•  ์ˆ˜ ์žˆ์—ˆ์Šต๋‹ˆ๋‹ค.

 

 

2. ์„ธ์…˜ ๊ด€๋ฆฌ ๊ฐ„์†Œํ™”

// ํ•œ ์ค„๋กœ ์‚ฌ์šฉ์ž ์ •๋ณด ์ ‘๊ทผ ๊ฐ€๋Šฅ
const { data: session } = useSession()

JWT ๊ธฐ๋ฐ˜ ์„ธ์…˜์„ ๊ธฐ๋ณธ ์ œ๊ณตํ•ด ์„œ๋ฒ„·ํด๋ผ์ด์–ธํŠธ ์–ด๋””์„œ๋“  ๋™์ผํ•œ ๋ฐฉ์‹์œผ๋กœ ์ ‘๊ทผํ•  ์ˆ˜ ์žˆ์—ˆ์Šต๋‹ˆ๋‹ค.
→ ๋กœ๊ทธ์ธ → ์‚ฌ์šฉ์ž ์ •๋ณด ํ™•์ธ → DB ์ €์žฅ ํ๋ฆ„์ด ์ผ๊ด€์„ฑ ์žˆ๊ฒŒ ์ด์–ด์กŒ์Šต๋‹ˆ๋‹ค.

 

 

3. ํ™•์žฅ์„ฑ

์นด์นด์˜ค ์™ธ์—๋„ Google, Github ๋“ฑ ๋‹ค์–‘ํ•œ Provider๋ฅผ ์‰ฝ๊ฒŒ ๋ถ™์ผ ์ˆ˜ ์žˆ์–ด, ์„œ๋น„์Šค ํ™•์žฅ ์‹œ ๋กœ๊ทธ์ธ ์ฑ„๋„์„ ๋Š˜๋ฆฌ๊ธฐ ์ˆ˜์›”ํ–ˆ์Šต๋‹ˆ๋‹ค.

ํŠนํžˆ ์นด์นด์˜ค ๋กœ๊ทธ์ธ์„ ์ง„ํ–‰ํ•˜๊ณ  ์‚ฌ์šฉ์ž ์ •๋ณด์— ์ ‘๊ทผํ•˜๋ ค๊ณ  ํ• ๋•Œ

CONST {data: session} = useSession()

 

์ด๋ ‡๊ฒŒ ๋‹จ ํ•œ ์ค„๋งŒ ์ž‘์„ฑํ•˜๋ฉด session ๊ฐ์ฒด ์•ˆ์—์„œ ๋กœ๊ทธ์ธํ•œ ์‚ฌ์šฉ์ž ์ •๋ณด๋ฅผ ๋ฐ”๋กœ ํ™œ์šฉํ•  ์ˆ˜ ์žˆ์—ˆ์Šต๋‹ˆ๋‹ค. ์ด๋Š” ์ง์ ‘ OAuth๋ฅผ ๊ตฌํ˜„ํ–ˆ์„ ๋•Œ์˜ ๋ณต์žกํ•œ ํ† ํฐ ํŒŒ์‹ฑ, API ํ˜ธ์ถœ ๊ณผ์ •์„ ์ƒ๋žตํ•˜๊ณ  ํ•œ์ค„๋กœ ์ž‘์„ฑํ•  ์ˆ˜ ์žˆ์–ด์„œ ๋งค์šฐ ํŽธํ–ˆ์Šต๋‹ˆ๋‹ค.

๊ฒฐ๊ตญ, Nextjs ํ’€์Šคํƒ ํ™˜๊ฒฝ์—์„œ ์ธ์ฆ๋ ˆ์ด์–ด๊นŒ์ง€ ์ž์—ฐ์Šค๋Ÿฝ๊ฒŒ NextJS ์ƒํƒœ๊ณ„์— ๋งž์ถฐ ํ•ด๊ฒฐํ•  ์ˆ˜ ์žˆ์—ˆ์Šต๋‹ˆ๋‹ค.

 


ORM : Prisma ์„ ํƒ

NextAuth๋กœ ์ธ์ฆ์„ ํ•ด๊ฒฐํ•œ ๋’ค, ๋ฐ์ดํ„ฐ ์ €์žฅ์†Œ๋กœ๋Š” MySQL์„ ์„ ํƒํ–ˆ์Šต๋‹ˆ๋‹ค. MySQL์€ ๊ฐ€์žฅ ๋Œ€์ค‘์ ์ด๊ณ  ์•ˆ์ •์ ์ธ ๊ด€๊ณ„ํ˜• DB์˜€๊ณ , ์ €ํฌ ํŒ€์€ ์œ ๋ ˆ์นด ๊ต์œก ๊ณผ์ •์—์„œ ์ด๋ฏธ Java + Spring + MySQL ์กฐํ•ฉ์„ ๊ฒฝํ—˜ํ•œ ์ ์ด ์žˆ์–ด ๋น ๋ฅด๊ฒŒ ์ ์‘ํ•  ์ˆ˜ ์žˆ์—ˆ์Šต๋‹ˆ๋‹ค.

๋‹ค๋งŒ SQL์„ ์ง์ ‘ ์ž‘์„ฑํ•˜๋Š” ๋ฐฉ์‹์€ ํ˜‘์—…๊ณผ ์œ ์ง€๋ณด์ˆ˜์— ๋ถˆํŽธํ•จ์ด ๋งŽ์•˜์Šต๋‹ˆ๋‹ค. ๊ทธ๋ž˜์„œ ORM(Object Relational Mapping) ๋„๊ตฌ๋ฅผ ๋„์ž…ํ•˜๊ธฐ๋กœ ํ–ˆ๊ณ , ๊ทธ์ค‘์—์„œ๋„ Prisma๋ฅผ ์„ ํƒํ–ˆ์Šต๋‹ˆ๋‹ค.

 


 

Java Spring๊ณผ Next.js๋น„๊ต

1. ORM ์ธก๋ฉด : Java์˜ MyBatis vs. Next.js์˜ Prisma

ํƒ€์ž… ์•ˆ์ „์„ฑ , ์ž๋™ ๋งˆ์ด๊ทธ๋ ˆ์ด์…˜

 

 

MyBatis๋Š” SQL ์ค‘์‹ฌ์˜ Mapper ๊ธฐ๋ฐ˜ ORM์œผ๋กœ ๊ฐœ๋ฐœ์ž๊ฐ€ ์ง์ ‘ SQL์„ ์ž‘์„ฑํ•˜๊ณ  ์ด๋ฅผ XML ํ˜น์€ annotation์„ ํ†ตํ•ด ๊ฐ์ฒด์™€ ๋งคํ•‘ํ•ฉ๋‹ˆ๋‹ค.

// MyBatis + Spring ์˜ˆ์‹œ
@PostMapping
public ResponseEntity<String> createPost(@RequestBody PostDto postDto) {
    postService.createPost(postDto);
}
<!-- PostMapper.xml -->
<insert id="insertPost">
    INSERT INTO posts (title, content) VALUES (#{title}, #{content})
</insert>

 

์ด๋Š” ๋ณต์žกํ•œ ์ฟผ๋ฆฌ๋‚˜ DB์— ํŠนํ™”๋œ ๋กœ์ง์„ ์„ธ๋ฐ€ํ•˜๊ฒŒ ์ œ์–ด๊ฐ€๋Š”๋ฐ ๊ฐ•์ ์ด ์žˆ์œผ๋ฉฐ, ๋Œ€๊ทœ๋ชจ ๊ธฐ์—… ์‹œ์Šคํ…œ์—์„œ ์„ ํ˜ธํ•˜๋Š” ๋ฐฉ์‹์ž…๋‹ˆ๋‹ค. ๋‹ค๋งŒ, ์ฟผ๋ฆฌ ์ž‘์„ฑ๊ณผ ๋งคํ•‘ ์„ค์ •์— ๋Œ€ํ•œ ๊ฐœ๋ฐœ์ž ์˜์กด๋„๊ฐ€ ๋†’์•„ ์ƒ์‚ฐ์„ฑ๊ณผ ์œ ์ง€ ๋ณด์ˆ˜ ์ธก๋ฉด์—์„œ ๋ถ€๋‹ด์ด ์žˆ์—ˆ์Šต๋‹ˆ๋‹ค.

 

 

๋ฐ˜๋ฉด, Prisma๋Š” ์ฝ”๋“œ ๊ธฐ๋ฐ˜์œผ๋กœ ์Šคํ‚ค๋งˆ๋ฅผ ์„ ์–ธํ•˜๊ณ  ์ด๋ฅผ ํ†ตํ•ด ํƒ€์ž… ์•ˆ์ „์„ฑ๊ณผ ์ž๋™ ์ฟผ๋ฆฌ ์ƒ์„ฑ์„ ์ง€์›ํ•˜๋Š” ORM์œผ๋กœ, SQL ์ถ”์ƒํ™” ์ˆ˜์ค€์ด ๋†’๊ณ  ํƒ€์ž…์Šคํฌ๋ฆฝํŠธ์™€ ์ž์—ฐ์Šค๋Ÿฝ๊ฒŒ ํ†ตํ•ฉ๋˜๋ฉฐ ๋ฐ์ดํ„ฐ ๋ชจ๋ธ๋ง ๋ฐ ๋งˆ์ด๊ทธ๋ ˆ์ด์…˜์ด ํšจ์œจ์ ์ž…๋‹ˆ๋‹ค. 

 


1. ํƒ€์ž… ์•ˆ์ „์„ฑ

  • Prisma๋Š” TypeScript ํ†ตํ•ฉ์„ ํ†ตํ•ด ์ฝ”๋“œ์™€ ๋ฐ์ดํ„ฐ๋ฒ ์ด์Šค ์Šคํ‚ค๋งˆ ๊ฐ„ ํƒ€์ž… ๋ถˆ์ผ์น˜ ๊ฐ์†Œ
  • ์ปดํŒŒ์ผ ๋‹จ๊ณ„์—์„œ ์˜ค๋ฅ˜ ๊ฒ€์ฆ ๊ฐ€๋Šฅ
// prisma/schema.prisma
model Post {
  id        Int      @id @default(autoincrement())
  title     String
  content   String
  createdAt DateTime @default(now())
}

 

2. ์ž๋™ ๋งˆ์ด๊ทธ๋ ˆ์ด์…˜ -> ๋น ๋ฅธ ๊ฐœ๋ฐœ ์†๋„

  • ๋ฐ์ดํ„ฐ๋ฒ ์ด์Šค ์Šคํ‚ค๋งˆ ๋ณ€๊ฒฝ ์‹œ ์ž๋™์œผ๋กœ SQL ๋งˆ์ด๊ทธ๋ ˆ์ด์…˜ ์ƒ์„ฑํ•˜๊ณ  ์ ์šฉ, ๊ฐœ๋ฐœ์ž๊ฐ€ ์ˆ˜๋™์œผ๋กœ ์Šคํ‚ค๋งˆ๋ฅผ ์—…๋ฐ์ดํŠธํ•˜๋Š” ์ˆ˜๊ณ ๋ฅผ ๋œ์–ด์ค๋‹ˆ๋‹ค.

 

3. ๊ฐœ๋ฐœ ํšจ์œจ์„ฑ

  • ๊ฐ„๊ฒฐํ•œ API(prisma.user.findUnique, prisma.post.create ๋“ฑ)๋ฅผ ์ œ๊ณตํ•˜์—ฌ ๋ฐ˜๋ณต์ ์ธ CRUD ์ฝ”๋“œ๋ฅผ ๋‹จ์ถ•์‹œ์ผœ์ค๋‹ˆ๋‹ค
// Next.js + Prisma ์˜ˆ์‹œ
const post = await prisma.post.create({
    data: { title, content },
});

 

์ด๋Š” ๋น ๋ฅธ ๊ฐœ๋ฐœ๊ณผ ์ผ๊ด€๋œ DB ๊ตฌ์กฐ ์œ ์ง€์— ์œ ๋ฆฌํ•˜๋ฉฐ ํŒ€์˜ TS ๊ธฐ๋ฐ˜ ํ”„๋ก ํŠธ์—”๋“œ ๊ฒฝํ—˜๊ณผ๋„ ์ž˜ ๋งž์•˜์Šต๋‹ˆ๋‹ค.

๊ฒฐ๊ณผ์ ์œผ๋กœ ์ €ํฌ๋Š” ๋น ๋ฅธ ๊ฐœ๋ฐœ๊ณผ ํ†ตํ•ฉ๋œ ๊ธฐ์ˆ ์Šคํƒ์„ ์ค‘์‹ฌ์œผ๋กœ Prisma ORM์„ ์„ ํƒํ–ˆ์Šต๋‹ˆ๋‹ค.

 


2. ์•„ํ‚คํ…์ฒ˜ ๋น„๊ต : Java์˜ MyBatis ๊ณ„์ธตํ˜• vs. Prisma API ์ค‘์‹ฌ ๊ตฌ์กฐ

๋ณต์žกํ•œ ๊ณ„์ธต์„ ์ตœ์†Œํ™”ํ•˜๊ณ  ์—”๋“œํฌ์ธํŠธ ์ค‘์‹ฌ์œผ๋กœ ๋น ๋ฅด๊ฒŒ API๋ฅผ ๊ตฌํ˜„ํ•  ์ˆ˜ ์žˆ์–ด, ์ดˆ๊ธฐ ๊ฐœ๋ฐœ ์†๋„์™€ ํ˜‘์—… ํšจ์œจ ํ–ฅ์ƒ

 

Java๋Š” ์ „ํ˜•์ ์ธ ๊ณ„์ธตํ˜• ์•„ํ‚คํ…์ฒ˜๋กœ Controller -> Servie -> Repository ๊ตฌ์กฐ๋กœ ๋ช…ํ™•ํ•˜๊ฒŒ ์—ญํ• ์„ ๋ถ„๋ฆฌํ•ฉ๋‹ˆ๋‹ค. ์ด๋Š” ๋Œ€๊ทœ๋ชจ ์‹œ์Šคํ…œ์— ์ ํ•ฉํ•˜๋ฉฐ ํ…Œ์ŠคํŠธ ์œ ์ง€๋ณด์ˆ˜ ๋ณด์•ˆ ์ธก๋ฉด์—๋„ ์œ ๋ฆฌํ•ฉ๋‹ˆ๋‹ค. ๊ทธ๋Ÿฌ๋‚˜ ์ดˆ๊ธฐ ์ง„์ž… ์žฅ๋ฒฝ์ด ๋†’๊ณ  ๊ฐ„๋‹จํ•œ ๊ธฐ๋Šฅ ๊ตฌํ˜„์—๋„ ์ฝ”๋“œ๊ฐ€ ๋ถ„์‚ฐ๋˜๊ณ  ๋ณต์žกํ•ด์งˆ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

[Controller] → [Service] → [Mapper] → [DB]

 

๋ฐ˜๋ฉด, Nextjs์˜ API Route ๊ตฌ์กฐ๋Š” ๋ผ์šฐํŒ…๊ณผ ๋กœ์ง์ด ํŒŒ์ผ๋‹จ์œ„๋กœ ๋ฌถ์—ฌ ์žˆ์–ด, ์—”๋“œํฌ์ธํŠธ ์ค‘์‹ฌ์œผ๋กœ ๊ตฌ์„ฑ๋ฉ๋‹ˆ๋‹ค. ๋ณต์žกํ•œ ๊ณ„์ธต ์—†์ด๋„ ๊ฐ„๋‹จํ•œ API ๊ธฐ๋Šฅ์„ ๋น ๋ฅด๊ฒŒ ๊ตฌํ˜„ํ•  ์ˆ˜ ์žˆ์œผ๋ฉฐ, page/api/* ํด๋” ๋งŒ์œผ๋กœ Rest API๋ฅผ ๊ตฌ์„ฑํ•  ์ˆ˜ ์žˆ๋‹ค๋Š” ์ ๋„ ์žฅ์ ์ž…๋‹ˆ๋‹ค. ๋‹ค๋งŒ ๊ทœ๋ชจ๊ฐ€ ์ปค์งˆ์ˆ˜๋ก ๋ชจ๋“ˆํ™” ์„ค๊ณ„๋‚˜ ๋ฏธ๋“ค์›จ์–ด ๊ตฌ์„ฑ์ด ํ•„์š”ํ•ฉ๋‹ˆ๋‹ค.

[API Route] → [Prisma Client] → [DB]

 

์ด๋Ÿฌํ•œ ๊ตฌ์กฐ์  ๊ฐ„๊ฒฐํ•จ์€ ํ”„๋กœ์ ํŠธ ์ดˆ๊ธฐ์— ์žฅ์ ์œผ๋กœ ์ž‘์šฉํ•˜์˜€์Šต๋‹ˆ๋‹ค.

 


๊ฒŒ์‹œ๊ธ€ ์ž‘์„ฑ API ์˜ˆ์ œ ๋น„๊ต

 

๊ฒŒ์‹œ๊ธ€์„ ์ž‘์„ฑํ•˜๋Š” API๋ฅผ ๊ฐ๊ฐ€ Java Spring๊ณผ Next๋กœ ๊ตฌํ˜„ํ•ด Next Prisma์˜ ๊ตฌ์กฐ์  ๋‹จ์ˆœํ•จ์„ ํ™•์ธํ•ด๋ณด๊ฒ ์Šต๋‹ˆ๋‹ค.

 

Java Spring + MyBatis (๊ณ„์ธตํ˜•)

// PostController.java
@RestController
@RequestMapping("/api/posts")
public class PostController {
  private final PostService postService;
  public PostController(PostService postService) { this.postService = postService; }

  @PostMapping
  public ResponseEntity<PostDto> create(@RequestBody PostDto dto) {
    return ResponseEntity.ok(postService.create(dto));
  }
}

์‚ฌ์šฉ์ž๊ฐ€ /api/posts ๋กœ POST ์š”์ฒญ์„ ๋ณด๋‚ด๋ฉด PostController ๊ฐ€ ์ด๋ฅผ ๋ฐ›๊ณ , ์‹ค์ œ ๋กœ์ง ์ฒ˜๋ฆฌ๋ฅผ ์œ„ํ•ด PostService๋กœ ์ „๋‹ฌํ•ฉ๋‹ˆ๋‹ค.

// PostService.java
@Service
public class PostService {
  private final PostMapper postMapper;
  public PostService(PostMapper postMapper) { this.postMapper = postMapper; }

  public PostDto create(PostDto dto) {
    postMapper.insertPost(dto);
    return dto;
  }
}
// PostMapper.java
@Mapper
public interface PostMapper {
  void insertPost(PostDto dto);
}

Mapper ์ธํ„ฐํŽ˜์ด์Šค๋ฅผ ํ†ตํ•ด ์‹ค์ œ SQL์„ ์‹คํ–‰ํ•˜๋Š” XML ํŒŒ์ผ๊ณผ ์—ฐ๊ฒฐํ•ฉ๋‹ˆ๋‹ค.

<!-- PostMapper.xml -->
<mapper namespace="com.example.PostMapper">
  <insert id="insertPost" parameterType="com.example.PostDto">
    INSERT INTO posts (title, content) VALUES (#{title}, #{content})
  </insert>
</mapper>

SQL ๋ฌธ์ด Mapper ์ธํ„ฐํŽ˜์ด์Šค์™€ ๋งคํ•‘๋˜์–ด ์‹คํ–‰๋ฉ๋‹ˆ๋‹ค.

// PostDto.java
@Data
public class PostDto {
  private String title;
  private String content;
}

๋ฐ์ดํ„ฐ๋ฅผ ๋‹ด๋Š” DTO ๊ฐ์ฒด

๊ฒŒ์‹œ๊ธ€ POST API ํ•˜๋‚˜๋ฅผ ๋งŒ๋“ค๊ธฐ ์œ„ํ•ด ์ด 5๊ฐœ์˜ ๊ณ„์ธต์  ํŒŒ์ผ์ด ํ•„์š”ํ•ฉ๋‹ˆ๋‹ค.

 

Nextjs (API Route + Prisma)

// prisma/schema.prisma
model Post {
  id        Int      @id @default(autoincrement())
  title     String
  content   String
  createdAt DateTime @default(now())
}
// app/api/posts/route.ts (Next.js App Router)
import { NextResponse } from "next/server";
import { prisma } from "@/lib/prisma";

export async function POST(req: Request) {
  const { title, content } = await req.json();
  const post = await prisma.post.create({ data: { title, content } });
  return NextResponse.json(post, { status: 200 });
}

 

 

shema.prisma ํŒŒ์ผ 1๊ฐœ๋กœ ๋ฐ์ดํ„ฐ ํ…Œ์ด๋ธ”์„ ์ •์˜ํ•˜๊ณ , NextJS์˜ API Route ์•ˆ์—์„œ Prisma Client๋ฅผ ๋ฐ”๋กœ ํ˜ธ์ถœํ•ด ๋น„์ฆˆ๋‹ˆ์Šค ๋กœ์ง๊ณผ ์—”๋“œํฌ์ธํŠธ๋ฅผ ๋™์‹œ์— ์ž‘์„ฑํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

 


๋งˆ๋ฌด๋ฆฌํ•˜๋ฉฐ

Java Spring์€ ๋Œ€๊ทœ๋ชจ ์‹œ์Šคํ…œ ๊ตฌ์ถ•์— ์ ํ•ฉํ•œ ์•ˆ์ •์„ฑ๊ณผ ํ™•์žฅ์„ฑ์„ ๊ฐ–์ถ˜ ํ”„๋ ˆ์ธ์›Œํฌ๋กœ, ๊ฒฌ๊ณ ํ•œ ์•„ํ‚คํ…์ฒ˜ ์„ค๊ณ„๊ฐ€ ํ•„์š”ํ•œ ํ™˜๊ฒฝ์—์„œ ์ ํ•ฉํ•ฉ๋‹ˆ๋‹ค.

๋ฐ˜๋ฉด, NextJS๋Š” ํ”„๋ก ํŠธ์—”๋“œ์™€ ๋ฐฑ์—”๋“œ๋ฅผ ํ†ตํ•ฉํ•ด ๋น ๋ฅด๊ณ  ๊ฐ„๋‹จํ•˜๊ฒŒ ๊ฐœ๋ฐœํ•  ์ˆ˜ ์žˆ๊ณ , TypeScript ๊ธฐ๋ฐ˜์˜ Prisma ORM๊ณผ์˜ ์กฐํ•ฉ์„ ํ†ตํ•ด ๋น„๊ต์  ๊ฐ€๋ฒผ์šด ์„œ๋น„์Šค ๊ตฌ์กฐ์— ์ ํ•ฉํ•œ ์ƒ์‚ฐ์„ฑ๊ณผ ์œ ์—ฐ์„ฑ์˜ ์žฅ์ ์ด ์žˆ์Šต๋‹ˆ๋‹ค.

 

์ฆ‰, Nextjs + Prisma ์กฐํ•ฉ์€ ์ œํ•œ๋œ ๋ฆฌ์†Œ์Šค์™€ ์‹œ๊ฐ„ ๋‚ด์—์„œ ์•ˆ์ •์ ์ด๊ณ  ํ™•์žฅ ๊ฐ€๋Šฅํ•œ ํ’€์Šคํƒ ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜์„ ๊ตฌ์ถ•ํ•  ์ˆ˜ ์žˆ๊ณ , ํ”„๋ก ํŠธ์—”๋“œ ์ค‘์‹ฌ์˜ ํŒ€ ๊ตฌ์„ฑ์œผ๋กœ ๋ฐฑ์—”๋“œ ๋ณต์žก์„ฑ์„ ์ตœ์†Œํ™”ํ•˜๋ฉด์„œ๋„ ํ•„์š”ํ•œ ๊ธฐ๋Šฅ์„ ๋น ๋ฅด๊ฒŒ ๊ตฌํ˜„ํ•  ์ˆ˜ ์žˆ๋‹ค๋Š” ์žฅ์ ์ด ์žˆ์–ด ์„ ํƒํ•˜์˜€์Šต๋‹ˆ๋‹ค.

 

 

 

์ฐธ๊ณ 

 

Prisma๋ž€? ๊ธฐ์—…๋“ค์˜ ์‚ฌ์šฉ ์‚ฌ๋ก€๋ถ€ํ„ฐ ์ ์šฉ ๋ฐฉ๋ฒ•๊นŒ์ง€์˜ ์‚ฌ์šฉ ์ข…ํ•ฉ ๊ฐ€์ด๋“œ I ์ด๋žœ์„œ ๋ธ”๋กœ๊ทธ

๋ณต์žกํ•œ ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜์„ ๊ฐœ๋ฐœํ•  ๋•Œ, ๋ฐ์ดํ„ฐ๋ฒ ์ด์Šค์™€์˜ ์—ฐ๋™์€ ๋”์šฑ ์ค‘์š”ํ•ด์ง€๋Š”๋ฐ, ์ด๋Ÿด ๋•Œ ๋ฐ์ดํ„ฐ ๋ฒ ์ด์Šค ์ž‘์—…์„ ํšจ์œจ์ ์œผ๋กœ ๋งŒ๋“ค์–ด์ฃผ๋Š” 'Prisma'์˜ ์‚ฌ์šฉ๋ฒ•์— ๋Œ€ํ•ด ์ด๋žœ์„œ์—์„œ ์ž์„ธํžˆ ์•Œ๋ ค๋“œ๋ฆฌ๊ฒ 

www.elancer.co.kr

 

728x90
'๐Ÿงก Projects/๐Ÿงก Projects: Web' ์นดํ…Œ๊ณ ๋ฆฌ์˜ ๋‹ค๋ฅธ ๊ธ€
  • [ ๋ฌด๋ฌผ ] ๊ทผ์ฒ˜ ์‚ฌ์šฉ์ž ์ฐพ๊ธฐ #2 : ์‹ค์‹œ๊ฐ„ ์‚ฌ์šฉ์ž ๊ฐ์ง€ ๋ฐ ์‚ฌ์šฉ์ž ์•„๋ฐ”ํƒ€ ๋ถˆ๋Ÿฌ์˜ค๊ธฐ
  • [ ๋ฌด๋ฌผ ] ๊ทผ์ฒ˜ ์‚ฌ์šฉ์ž ์ฐพ๊ธฐ #3 : ๋‚˜์™€ ๋™์ผํ•œ ํ”„๋กœํ•„ ์œ ํ˜• ํด๋ฆญํ•˜๋ฉด ์Šคํƒฌํ”„ ์ ๋ฆฝ ๋ฐ ์‹ค์‹œ๊ฐ„ ์•Œ๋ฆผ ์• ๋‹ˆ๋ฉ”์ด์…˜
  • [BADATA] ์œ„์น˜ ๊ฒ€์ƒ‰ ์ฐฝ์— ๋””๋ฐ”์šด์‹ฑ ์“ฐ๋กœํ‹€๋ง ์ค‘์ฒฉ ๋ฌธ์ œ ํ•ด๊ฒฐํ•˜๊ธฐ
  • [์œ ๋ ˆ์นด] github์— html ๋ฐฐํฌ ์‹œ ์˜์ƒ, ์‚ฌ์ง„ ์•ˆ ๋ณด์ด๋Š” ๋ฌธ์ œ ํ•ด๊ฒฐ
eyes from es
eyes from es
  • eyes from es
    eyes from es
    eyes from es
  • ์ „์ฒด
    ์˜ค๋Š˜
    ์–ด์ œ
    • ๋ถ„๋ฅ˜ ์ „์ฒด๋ณด๊ธฐ
      • โค๏ธ ๊ฟ€ํŒ ๋ชจ์Œ
        • โค๏ธ ๊ฐ“์ƒ ๊ฟ€ํŒ
        • โค๏ธ ํ”„๋กœ๊ทธ๋ž˜๋ฐ
      • ๐Ÿงก Projects
        • ๐Ÿงก Projects: Web
        • ๐ŸŽคPreterview
        • ๐Ÿงก Projects: App
        • ๐Ÿงก๋Œ€์™ธํ™œ๋™
        • ๐Ÿงก OSCCA ์˜คํ”ˆ์†Œ์Šค ์ปจํŠธ๋ฆฌ๋ทฐ์…˜ ์•„์นด๋ฐ๋ฏธ
      • ๐Ÿ’› Frontend
        • ๐Ÿ’› Frontend : React
        • ๐Ÿ’› Frontend : JavaScript
        • ๐Ÿ’› Frontend : TypeScript
      • ๐Ÿ’š Backend
      • ๐Ÿ’™ OS: ์šด์˜์ฒด์ œ
        • ๐Ÿ’™ Linux
      • ๐Ÿ’œ ์ฝ”๋”ฉํ…Œ์ŠคํŠธ
        • ๐Ÿ’œ ์ž๋ฃŒ๊ตฌ์กฐ
        • ๐Ÿ’œ ์•Œ๊ณ ๋ฆฌ์ฆ˜
        • ๐Ÿ’œ ๋ฐฑ์ค€
        • ๐Ÿ’œSWEA
        • ๐Ÿ’œํ”„๋กœ๊ทธ๋ž˜๋จธ์Šค
      • ๐Ÿ”ด Study
        • ๐Ÿ”ด๋ฉด์ ‘ ์Šคํ„ฐ๋””
        • ๐Ÿ”ด ๊ธฐ์—…๋ถ„์„
        • ๐Ÿ”ด ์—๋Ÿฌ๋…ธํŠธ(Error Note)๐Ÿงฑ
        • ๐Ÿ”ด ITNews(Coding)
        • ๐Ÿ”ด ITNews(Tech)
      • ๐ŸŸ  ์ธ์ƒ ๊ณ„ํš
        • ๐ŸŸ  ์˜ฌํ•ด ๋ชฉํ‘œ
      • ๐ŸŸก TIL
        • ๐ŸŸก TIL ์ผ๊ธฐ
  • ๋ธ”๋กœ๊ทธ ๋ฉ”๋‰ด

    • ํ™ˆ
    • ํƒœ๊ทธ
    • ๋ฐฉ๋ช…๋ก
  • ๋งํฌ

  • ๊ณต์ง€์‚ฌํ•ญ

  • ์ธ๊ธฐ ๊ธ€

  • ํƒœ๊ทธ

    ์ž๋ฃŒ๊ตฌ์กฐ
    html
    ์ตœ๊ทผ์ด์Šˆ
    ๋„ค์นด๋ผ์ฟ ๋ฐฐ
    ๋ฌธ์ œํ’€์ด
    ์ŠคํŒŒ๋ฅดํƒ€์ฝ”๋”ฉํด๋Ÿฝ
    ์ฝ”ํ…Œ
    ๋ถ„์„๋ ˆํฌํŠธ
    ์‚ผ์„ฑ์ „์ž
    ์Šค๋งˆํŠธ์‹ฑ์Šค
    IT์ด์Šˆ
    ์ฝ”๋“œ์Šคํ„ฐ๋””
    ๋‰ด์Šค์Šคํฌ๋žฉ
    ๋‰ด์Šค๋ฃธ
    SW์ด์Šˆ
    ๊ธฐ์—…๋ถ„์„
    css
    ๊ฐœ๋ฐœ
    ์•Œ๊ณ ๋ฆฌ์ฆ˜
    ์Šคํ„ฐ๋””
    ๋ฐฉํ•™์Šคํ„ฐ๋””
    ์ฝ”๋”ฉ
    ๊ฐœ๋ฐœ๊ณต๋ถ€
    ๋ฐฑ์ค€
    ๋™ํ–ฅ๋ถ„์„
    ์ฝ”๋“œ๋ฆฌ๋ทฐ
    Ai
    ์ฝ”๋”ฉํ…Œ์ŠคํŠธ
    C
    ์›น๊ฐœ๋ฐœ
  • ์ตœ๊ทผ ๋Œ“๊ธ€

  • ์ตœ๊ทผ ๊ธ€

  • hELLOยท Designed By์ •์ƒ์šฐ.v4.10.5
eyes from es
[ ๋ฌด๋ฌผ ] Prisma ORM ์œผ๋กœ NextJS ๋ฐฑ์—”๋“œ ์„œ๋ฒ„ ๊ตฌ์ถ•ํ•˜๊ธฐ
์ƒ๋‹จ์œผ๋กœ

ํ‹ฐ์Šคํ† ๋ฆฌํˆด๋ฐ”