๋ณธ๋ฌธ ๋ฐ”๋กœ๊ฐ€๊ธฐ
  • What would life be If we had no courage to attemp anything?
๐“๐จ๐๐š๐ฒ ๐ˆ ๐‹๐ž๐š๐ซ๐ง

์‹ค์‹œ๊ฐ„ ์•Œ๋ฆผ ๊ตฌํ˜„ ํ•˜๊ธฐ : 4. ํ•˜๋‚˜์˜ ์ฑ„๋„๋กœ SSE ํ†ต์‹ ํ•˜๊ธฐ (with. Shared Worker)

by DevIseo 2025. 12. 7.

์ด์ „๊ธ€์—์„œ SSE ์—ฐ๊ฒฐ ํ…Œ์ŠคํŠธ๋ฅผ ๋งˆ์นœํ›„์— ์‹ค์ œ๋กœ ๊ฐœ๋ฐœ์— ์ฐฉ์ˆ˜ํ•˜๋Š” ๋‹จ๊ณ„๊ฐ€ ๋˜์—ˆ๋‹ค. ๊ฐœ๋ฐœ ์ด์ „์— ๋‚ด๊ฐ€ ๊ณ ๋ คํ•ด์•ผ ํ•  ์‚ฌํ•ญ๋“ค์— ๋Œ€ํ•ด ์ •๋ฆฌ๋ฅผ ํ•ด๋ณด์•˜๋‹ค.

 

1. SSE๋Š” ๋ธŒ๋ผ์šฐ์ € ํƒญ๋งˆ๋‹ค ์—ฐ๊ฒฐ์ด ์ƒˆ๋กœ ์—ด๋ฆฐ๋‹ค.

2. ํ—ค๋” ์ปค์Šคํ…€์ด ํ•„์š”ํ•˜์ง€๋งŒ SSE์˜ ๊ฒฝ์šฐ ํ—ค๋” ์ปค์Šคํ…€์ด ๋ถˆ๊ฐ€๋Šฅํ•˜๋‹ค.

 

์ด ์กฐ๊ฑด์„ ๋™์‹œ์— ๋งŒ์กฑ์‹œํ‚ค๋Š” ๊ตฌ์กฐ๋ฅผ ๋งŒ๋“œ๋Š” ๊ฒƒ์ด ์ด๋ฒˆ ์‹ค์‹œ๊ฐ„ ์•Œ๋ฆผ ๊ฐœ๋ฐœ์˜ ํ•ต์‹ฌ ๊ณผ์ œ์˜€๋‹ค.

 

1. ํƒญ๋งˆ๋‹ค ์ƒˆ๋กœ ์—ด๋ฆฌ๋Š” SSE ์—ฐ๊ฒฐ ๋ฌธ์ œ

SSE๋Š” ๊ธฐ๋ณธ์ ์œผ๋กœ ๋ธŒ๋ผ์šฐ์ € ํƒญ ๋‹จ์œ„๋กœ ์—ฐ๊ฒฐ์ด ์ƒ์„ฑ๋œ๋‹ค.
์ฆ‰, ์‚ฌ์šฉ์ž๊ฐ€ ๊ฐ™์€ ์„œ๋น„์Šค์—์„œ ํƒญ์„ 3๊ฐœ ์—ด๋ฉด ์„œ๋ฒ„ ์ž…์žฅ์—์„œ๋Š” SSE ์—ฐ๊ฒฐ์ด 3๊ฐœ๊ฐ€ ์—ด๋ฆฐ๋‹ค.

 

๊ธฐ์ˆ  ๊ฒ€ํ†  ์ดˆ๊ธฐ์—๋Š” ์ด ๋ถ€๋ถ„์„ ํฌ๊ฒŒ ๋ฌธ์ œ ์‚ผ์ง€ ์•Š์•˜๋‹ค.
ํ•˜์ง€๋งŒ ์‹ค์‹œ๊ฐ„ ์•Œ๋ฆผ์€ ํŠน์ • ํŽ˜์ด์ง€๊ฐ€ ์•„๋‹ˆ๋ผ ํ—ค๋”์— ํ•ญ์ƒ ๋–  ์žˆ์–ด์•ผ ํ•˜๋Š” ๊ธฐ๋Šฅ์ด์—ˆ๊ณ , ์ž์—ฐ์Šค๋Ÿฝ๊ฒŒ ์‚ฌ์šฉ์ž๋Š” ์—ฌ๋Ÿฌ ํƒญ์„ ์—ด์–ด๋‘” ์ƒํƒœ์—์„œ๋„ ๋™์ผํ•œ ์•Œ๋ฆผ์„ ๋™์‹œ์— ๋ฐ›์•„์•ผ ํ–ˆ๋‹ค. ์ด ๊ตฌ์กฐ๋ฅผ ๊ทธ๋Œ€๋กœ ๋‘๋ฉด ๋‹ค์Œ๊ณผ ๊ฐ™์€ ๋ฌธ์ œ๊ฐ€ ์ƒ๊ธด๋‹ค.

  • ์„œ๋ฒ„ ์ž…์žฅ์—์„œ ๊ฐ™์€ ์œ ์ €์—๊ฒŒ ์ค‘๋ณต๋œ SSE ์—ฐ๊ฒฐ์ด ๊ณ„์† ์—ด๋ฆฐ๋‹ค
  • ํŠธ๋ž˜ํ”ฝ๊ณผ ์ปค๋„ฅ์…˜ ์ˆ˜๊ฐ€ ์‚ฌ์šฉ์ž ์ˆ˜ × ํƒญ ์ˆ˜๋งŒํผ ์ฆ๊ฐ€ํ•œ๋‹ค
  • ์‹ค์„œ๋น„์Šค ํ™˜๊ฒฝ์—์„œ๋Š” ๋น„์šฉ๊ณผ ์•ˆ์ •์„ฑ ๋ชจ๋‘์— ๋ถ€๋‹ด์ด ๋œ๋‹ค

์ฆ‰, “ํƒญ๋งˆ๋‹ค SSE๋ฅผ ์—ฌ๋Š” ๊ตฌ์กฐ๋Š” ๊ธฐ์ˆ ์ ์œผ๋กœ๋Š” ๊ฐ„๋‹จํ•˜์ง€๋งŒ, ์šด์˜ ์ธก๋ฉด์—์„œ๋Š” ๋งค์šฐ ๋น„ํšจ์œจ์ ”์ด๋ผ๋Š” ๊ฒฐ๋ก ์— ๋„๋‹ฌํ•˜๊ฒŒ ๋˜์—ˆ๋‹ค.

 

 

2. SSE๋Š” ํ—ค๋” ์ปค์Šคํ…€์ด ๋ถˆ๊ฐ€๋Šฅํ•˜๋‹ค๋Š” ์ œ์•ฝ

๋งˆ์ง€๋ง‰์œผ๋กœ ๊ฐ€์žฅ ํ˜„์‹ค์ ์ธ ์ œ์•ฝ์ด ํ•˜๋‚˜ ๋” ์žˆ์—ˆ๋‹ค. ๋ฐ”๋กœ SSE๋Š” ๊ธฐ๋ณธ EventSource API๋กœ๋Š” ์ปค์Šคํ…€ ํ—ค๋”๋ฅผ ๋„ฃ์„ ์ˆ˜ ์—†๋‹ค๋Š” ์ ์ด๋‹ค.

์šฐ๋ฆฌ ์„œ๋น„์Šค๋Š” ์ธ์ฆ ๊ตฌ์กฐ๊ฐ€ ๋‹ค์Œ๊ณผ ๊ฐ™์•˜๋‹ค.

  • API ์š”์ฒญ ์‹œ Authorization: Bearer accessToken ํ•„์š”
  • ์ผ๋ถ€ ํ™˜๊ฒฝ์—์„œ๋Š” ์ฟ ํ‚ค ๊ธฐ๋ฐ˜ ์ธ์ฆ๊ณผ ํ—ค๋” ์ธ์ฆ์„ ํ•จ๊ป˜ ์‚ฌ์šฉ

ํ•˜์ง€๋งŒ ๊ธฐ๋ณธ EventSource๋Š” ๋‹ค์Œ๊ณผ ๊ฐ™์€ ํ•œ๊ณ„๋ฅผ ๊ฐ€์ง„๋‹ค.

  • Authorization ํ—ค๋”๋ฅผ ์ง์ ‘ ๋„ฃ์„ ์ˆ˜ ์—†์Œ
  • ์ฆ‰, ๊ธฐ์กด ์ธ์ฆ ๋ฐฉ์‹ ๊ทธ๋Œ€๋กœ๋Š” SSE ์ธ์ฆ์ด ๋ถˆ๊ฐ€๋Šฅํ•œ ๊ตฌ์กฐ

๋ฌผ๋ก  event-source-polyfill ๊ฐ™์€ ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ๋ฅผ ํ™œ์šฉํ•˜๋ฉด ํ—ค๋”๋ฅผ ์ถ”๊ฐ€ํ•  ์ˆ˜๋Š” ์žˆ์—ˆ๋‹ค.

ํ•˜์ง€๋งŒ ์ด ๋ฐฉ์‹์€ 1๋ฒˆ ๋ฌธ์ œ๋ฅผ ํ•ด๊ฒฐํ•˜๊ธฐ ์œ„ํ•ด ์‚ฌ์šฉํ–ˆ๋˜ Shared Worker์™€ ํ•จ๊ป˜ ์‚ฌ์šฉํ•˜๊ธฐ์—๋Š” ์—ฌ๋Ÿฌ ์ œ์•ฝ์ด ์กด์žฌํ–ˆ๋‹ค.

 

ํŠนํžˆ Shared Worker๋Š”

  • next.js์—์„œ public ๊ฒฝ๋กœ์˜ ์ˆœ์ˆ˜ .js ํŒŒ์ผ์—์„œ ๋™์ž‘ํ•ด์•ผ ํ•˜๊ณ 
  • ๋ฒˆ๋“ค๋ง๋œ ๋ชจ๋“ˆ์„ import ํ•˜๋Š” ๊ฒƒ๋„ ์ œํ•œ์ ์ด๋ฉฐ
  • ๋ณด์•ˆ์ƒ ํ† ํฐ์„ URL query๋กœ ๋„˜๊ธฐ๋Š” ๋ฐฉ์‹ ์—ญ์‹œ ๋ถ€๋‹ด์ด ์ปธ๋‹ค

๊ฒฐ๊ตญ ๋‚˜๋Š” ์ด๋ ‡๊ฒŒ ์ •๋ฆฌํ•˜๊ฒŒ ๋˜์—ˆ๋‹ค.

“SSE ์ธ์ฆ ๋ฌธ์ œ๋Š” ํด๋ผ์ด์–ธํŠธ์—์„œ ์–ต์ง€๋กœ ํ•ด๊ฒฐํ•  ๊ฒŒ ์•„๋‹ˆ๋ผ, ์ค‘๊ฐ„์—์„œ ํ•œ ๋ฒˆ ๋” ์ œ์–ดํ•  ์ˆ˜ ์žˆ๋Š” ๋ ˆ์ด์–ด๊ฐ€ ํ•„์š”ํ•˜๊ฒ ๋‹ค.”

 

 

๊ทธ๋ž˜์„œ ๊ตฌ์กฐ๋ฅผ ‘ํ”„๋ก์‹œ ๊ธฐ๋ฐ˜’์œผ๋กœ ๋‹ค์‹œ ๋ณด๊ธฐ ์‹œ์ž‘ํ–ˆ๋‹ค

์ด ๋‘ ๊ฐ€์ง€ ๋ฌธ์ œ๋ฅผ ์ข…ํ•ฉํ•˜๋ฉด ๋‹ค์Œ๊ณผ ๊ฐ™์€ ๊ฒฐ๋ก ์— ๋„๋‹ฌํ•˜๊ฒŒ ๋œ๋‹ค.

  • SSE ์—ฐ๊ฒฐ์€ ๊ฐ€๋Šฅํ•˜๋ฉด ํ•˜๋‚˜๋งŒ ์œ ์ง€ํ•˜๊ณ  ์‹ถ๊ณ 
  • ์ธ์ฆ ํ—ค๋”๋Š” ์•ˆ์ „ํ•˜๊ฒŒ ์‹ค์–ด์„œ ์ „๋‹ฌํ•ด์•ผ ํ•œ๋‹ค

์ด ๋‘ ์š”๊ตฌ์‚ฌํ•ญ์„ ๋™์‹œ์— ๋งŒ์กฑ์‹œํ‚ค๊ธฐ ์œ„ํ•ด, ๋‚˜๋Š” SSE๋ฅผ ์ง์ ‘ ๋ฐฑ์—”๋“œ์— ๋ถ™์ด๋Š” ๊ตฌ์กฐ๊ฐ€ ์•„๋‹ˆ๋ผ,
์ด์ „ ๊ธ€์—์„œ ๋ฐœ์ƒํ–ˆ๋˜ Next.js์˜ gzip ์ด์Šˆ ํ•ด๊ฒฐ์„ ์œ„ํ•ด ๊ณ ๋ ค๋˜์—ˆ๋˜ Next.js API Routes๋ฅผ ๊ฑฐ์น˜๋Š” ๊ตฌ์กฐ๋กœ ๊ฐ€์ ธ๊ฐ€๊ธฐ๋กœ ํ™•์ •ํ–ˆ๋‹ค.

 

 

 

โœ… API Routes๋ฅผ SSE ํ”„๋ก์‹œ๋กœ ์‚ฌ์šฉํ•˜๊ธฐ๋กœ ํ•œ ์ด์œ 

Next.js API Routes๋ฅผ ์ค‘๊ฐ„์— ๋‘๋Š” ๊ตฌ์กฐ๋Š” ์ฒ˜์Œ๋ถ€ํ„ฐ ์˜๋„ํ•œ ์„ ํƒ์€ ์•„๋‹ˆ์—ˆ๋‹ค.
ํ•˜์ง€๋งŒ ์ง€๊ธˆ ์™€์„œ ๋Œ์•„๋ณด๋ฉด, ์ด ์„ ํƒ ํ•˜๋‚˜๋กœ ๋‹ค์Œ ๋ฌธ์ œ๋“ค์ด ํ•œ ๋ฒˆ์— ์ •๋ฆฌ๋˜๊ธฐ ์‹œ์ž‘ํ–ˆ๋‹ค.


1๏ธโƒฃ gzip ์••์ถ•์œผ๋กœ ์ธํ•ด SSE ์‹ค์‹œ๊ฐ„์„ฑ์ด ๊นจ์ง€๋Š” ๋ฌธ์ œ ํ•ด๊ฒฐ

๊ธฐ์กด์—๋Š” next.config.js์˜ rewrites๋ฅผ ํ†ตํ•ด
ํ”„๋ก ํŠธ์—์„œ ๋ฐฑ์—”๋“œ SSE ์„œ๋ฒ„๋กœ ์ง์ ‘ ์—ฐ๊ฒฐํ•˜๋Š” ๊ตฌ์กฐ๋ฅผ ์‚ฌ์šฉํ•˜๊ณ  ์žˆ์—ˆ๋‹ค.

ํ•˜์ง€๋งŒ Next.js์˜ ๊ธฐ๋ณธ ์˜ต์…˜์ธ compress: true๋กœ ์ธํ•ด:

  • ์‘๋‹ต์ด gzip์œผ๋กœ ์••์ถ•๋˜๋ฉด์„œ
  • ์ถฉ๋ถ„ํ•œ ๋ฐ์ดํ„ฐ๊ฐ€ ์Œ“์ด๊ธฐ ์ „๊นŒ์ง€ ์‘๋‹ต์ด ๋ฒ„ํผ๋ง๋˜๊ณ 
  • ๊ทธ ๊ฒฐ๊ณผ SSE์˜ ์‹ค์‹œ๊ฐ„์„ฑ์ด ์™„์ „ํžˆ ๊นจ์ง€๋Š” ํ˜„์ƒ์ด ๋ฐœ์ƒํ–ˆ๋‹ค.

๋ฐ˜๋ฉด API Routes๋Š”:

  • Next.js์˜ gzip ์••์ถ• ์˜ˆ์™ธ ๊ฒฝ๋กœ์— ํ•ด๋‹นํ•˜๊ณ 
  • ์ŠคํŠธ๋ฆฌ๋ฐ ์‘๋‹ต์„ ๋ฒ„ํผ๋ง ์—†์ด ๊ทธ๋Œ€๋กœ ์ „๋‹ฌํ•  ์ˆ˜ ์žˆ๋Š” ๊ตฌ์กฐ์˜€๋‹ค.

์ฆ‰, API Routes๋ฅผ ํ”„๋ก์‹œ๋กœ ์‚ฌ์šฉํ•˜๋ฉด, gzip ๋ฌธ์ œ๋ฅผ ๊ตฌ์กฐ์ ์œผ๋กœ ํšŒํ”ผํ•  ์ˆ˜ ์žˆ์—ˆ๋‹ค.


2๏ธโƒฃ SSE ์ธ์ฆ ๋ฌธ์ œ๋ฅผ ์„œ๋ฒ„ ์‚ฌ์ด๋“œ์—์„œ ํ•ด๊ฒฐํ•  ์ˆ˜ ์žˆ๋‹ค

์•ž์„œ ์–ธ๊ธ‰ํ–ˆ๋“ฏ์ด, ๊ธฐ๋ณธ EventSource๋Š” Authorization ํ—ค๋”๋ฅผ ์ง์ ‘ ๋„ฃ์„ ์ˆ˜ ์—†๋‹ค.
ํ•˜์ง€๋งŒ API Routes๋ฅผ ๊ฑฐ์น˜๊ฒŒ ๋˜๋ฉด ์ƒํ™ฉ์ด ์™„์ „ํžˆ ๋‹ฌ๋ผ์ง„๋‹ค.

  • ํด๋ผ์ด์–ธํŠธ → API Routes ์š”์ฒญ์—๋Š” ์ฟ ํ‚ค๊ฐ€ ์ž๋™์œผ๋กœ ํฌํ•จ๋˜๊ณ 
  • API Routes์—์„œ๋Š” ๊ทธ ์ฟ ํ‚ค๋ฅผ ์ฝ์–ด
  • ๋ฐฑ์—”๋“œ SSE ์š”์ฒญ ์‹œ Authorization: Bearer token ํ—ค๋”๋ฅผ ์ง์ ‘ ๊ตฌ์„ฑํ•ด์„œ ์ „๋‹ฌํ•  ์ˆ˜ ์žˆ๋‹ค.

์ฆ‰, ํด๋ผ์ด์–ธํŠธ์—์„œ๋Š” ๋” ์ด์ƒ ์ธ์ฆ์„ ์‹ ๊ฒฝ ์“ธ ํ•„์š”๊ฐ€ ์—†์–ด์ง€๊ณ , SSE ์ธ์ฆ ๋กœ์ง์€ ์ „๋ถ€ ์„œ๋ฒ„ ์‚ฌ์ด๋“œ์—์„œ ์ผ๊ด€๋˜๊ฒŒ ์ฒ˜๋ฆฌํ•  ์ˆ˜ ์žˆ๊ฒŒ ๋˜์—ˆ๋‹ค.


3๏ธโƒฃ ์ดํ›„ Shared Worker ๊ตฌ์กฐ๊นŒ์ง€ ์ž์—ฐ์Šค๋Ÿฝ๊ฒŒ ์—ฐ๊ฒฐํ•  ์ˆ˜ ์žˆ๋‹ค

๊ทธ๋ฆฌ๊ณ  ์ด ๊ตฌ์กฐ๋Š” ์ž์—ฐ์Šค๋Ÿฝ๊ฒŒ, “SSE ์—ฐ๊ฒฐ์€ ๋ฌด์กฐ๊ฑด API Routes ํ•œ ๊ณณ์œผ๋กœ๋งŒ ๋ชจ์€๋‹ค”๋ผ๋Š” ์ „์ œ ์กฐ๊ฑด์„ ๋งŒ๋“ค์–ด์ฃผ์—ˆ๋‹ค.

์ด ๋ง์€ ๊ณง,

  • Shared Worker์—์„œ SSE๋ฅผ ์—ด๋”๋ผ๋„
  • ํ•ญ์ƒ /api/sse/event๋ผ๋Š” ํ•˜๋‚˜์˜ ๊ณ ์ •๋œ ์—”๋“œํฌ์ธํŠธ๋งŒ ๋ฐ”๋ผ๋ณด๊ฒŒ ๋˜๊ณ 
  • ๋‚ด๋ถ€ ๊ตฌ์กฐ๊ฐ€ ์–ด๋–ป๋“ , ํด๋ผ์ด์–ธํŠธ์™€ ๋ฐฑ์—”๋“œ ์‚ฌ์ด์˜ ์ ‘์ ์€ ๋‹จ ํ•˜๋‚˜๋กœ ์ˆ˜๋ ด๋œ๋‹ค.

์ด ๋•๋ถ„์— ์ดํ›„์—:

  • Shared Worker์—์„œ SSE๋ฅผ ํ•˜๋‚˜๋งŒ ์—ด๊ณ 
  • ์—ฌ๋Ÿฌ ํƒญ์œผ๋กœ ๋ธŒ๋กœ๋“œ์บ์ŠคํŠธํ•˜๋Š” ๊ตฌ์กฐ๋ฅผ ์„ค๊ณ„ํ•˜๋Š” ๋ฐ์—๋„ ํฐ ๋ฐฉํ–ฅ์„ฑ ์ˆ˜์ • ์—†์ด ๊ทธ๋Œ€๋กœ ํ™•์žฅํ•  ์ˆ˜ ์žˆ์—ˆ๋‹ค.

์ •๋ฆฌํ•ด ๋ณด๋ฉด

Next.js API Routes๋ฅผ SSE ํ”„๋ก์‹œ๋กœ ์‚ฌ์šฉํ•˜๊ธฐ๋กœ ํ•œ ๊ฒฐ์ •์€, ๋‹จ์ˆœํžˆ “์šฐํšŒ ๊ฒฝ๋กœ๋ฅผ ํ•˜๋‚˜ ์ถ”๊ฐ€ํ•œ ๊ฒƒ”์ด ์•„๋‹ˆ์—ˆ๋‹ค.

์ด ์„ ํƒ ํ•˜๋‚˜๋กœ ์ด ์„ธ ๊ฐ€์ง€๊ฐ€ ํ•œ ๋ฒˆ์— ์ •๋ฆฌ๋˜๊ธฐ ์‹œ์ž‘ํ–ˆ๋‹ค.

  • โœ… gzip์œผ๋กœ ์ธํ•œ SSE ์ง€์—ฐ ๋ฌธ์ œ
  • โœ… SSE ์ธ์ฆ ํ—ค๋” ์ „๋‹ฌ ๋ฌธ์ œ
  • โœ… Shared Worker ๋‹จ์ผ ์ฑ„๋„ ๊ตฌ์กฐ ์„ค๊ณ„์˜ ๊ธฐ๋ฐ˜

 

 

 

์ด์ œ SSE๋Š” ํ•ญ์ƒ /api/sse/event๋ฅผ ํ†ตํ•ด์„œ๋งŒ ์—ด๋ฆฌ๊ฒŒ ๋˜์—ˆ๊ณ ,
ํ”„๋ก ํŠธ์—”๋“œ ์ž…์žฅ์—์„œ๋Š” “์ธ์ฆ๊ณผ gzip ๋ฌธ์ œ๋Š” ๋” ์ด์ƒ ์‹ ๊ฒฝ ์“ฐ์ง€ ์•Š์•„๋„ ๋˜๋Š” ์ƒํƒœ”๊ฐ€ ๋˜์—ˆ๋‹ค.

ํ•˜์ง€๋งŒ ์—ฌ์ „ํžˆ ํ•ด๊ฒฐ๋˜์ง€ ์•Š์€ ๋ฌธ์ œ๊ฐ€ ํ•˜๋‚˜ ๋‚จ์•„ ์žˆ์—ˆ๋‹ค.

“SSE ์—ฐ๊ฒฐ์€ ํ•˜๋‚˜๋งŒ ์œ ์ง€ํ•˜๊ณ  ์‹ถ๋‹ค.”

API Routes๊ฐ€ ์ค‘๊ฐ„์— ์ƒ๊ธฐ๋ฉด์„œ ๊ตฌ์กฐ๋Š” ์ •๋ฆฌ๋˜์—ˆ์ง€๋งŒ, ์—ฌ์ „ํžˆ ๋ธŒ๋ผ์šฐ์ € ํƒญ๋งˆ๋‹ค /api/sse/event๋กœ SSE ์—ฐ๊ฒฐ์„ ์ƒˆ๋กœ ์—ด๊ณ  ์žˆ๋‹ค๋Š” ์‚ฌ์‹ค ์ž์ฒด๋Š” ๋ณ€ํ•˜์ง€ ์•Š์•˜๋‹ค.

์ฆ‰, ๊ตฌ์กฐ๋Š” ์•ˆ์ „ํ•ด์กŒ์ง€๋งŒ, ์—ฐ๊ฒฐ ์ˆ˜ ์ž์ฒด๋ฅผ ์ค„์ด๋Š” ๋ฌธ์ œ๋Š” ์•„์ง ํ•ด๊ฒฐ๋˜์ง€ ์•Š์€ ์ƒํƒœ์˜€๋‹ค.

 

 

โœ… ๊ทธ๋ž˜์„œ ๋‹ค์‹œ ๋งˆ์ฃผํ•œ ๋ฌธ์ œ: “ํƒญ์ด ์—ฌ๋Ÿฌ ๊ฐœ๋ฉด SSE๋„ ์—ฌ๋Ÿฌ ๊ฐœ๋‹ค”

ํ˜„์‹ค์ ์ธ ์‚ฌ์šฉ ์‹œ๋‚˜๋ฆฌ์˜ค๋ฅผ ๋‹ค์‹œ ๋– ์˜ฌ๋ ค ๋ณด๋ฉด ๋‹ค์Œ๊ณผ ๊ฐ™์•˜๋‹ค.

  • ์‚ฌ์šฉ์ž๋Š” ๋ฉ”์ธ ํ™”๋ฉด์„ ์ผœ ๋‘” ์ƒํƒœ์—์„œ
  • ์ƒˆ๋กœ์šด ๊ธฐ๋Šฅ์„ ๋ณด๊ฒ ๋‹ค๊ณ  ํƒญ์„ ํ•˜๋‚˜ ๋” ์—ด๊ณ 
  • ํ•„์š”ํ•˜๋ฉด ๋˜ ํ•˜๋‚˜๋ฅผ ๋” ์—ฐ๋‹ค

UI๋Š” ์ „๋ถ€ ๋™์ผํ•˜๊ณ ,
ํ—ค๋”์—๋Š” ๋™์ผํ•œ ์‹ค์‹œ๊ฐ„ ์•Œ๋ฆผ ์ข… ์•„์ด์ฝ˜์ด ๋–  ์žˆ๋‹ค.

ํ•˜์ง€๋งŒ ๊ธฐ์ˆ ์ ์œผ๋กœ๋Š”:

  • ๊ฐ ํƒญ์ด ์ „๋ถ€ ๋…๋ฆฝ์ ์œผ๋กœ /api/sse/event์— ์—ฐ๊ฒฐ
  • ๊ฒฐ๊ณผ์ ์œผ๋กœ ๊ฐ™์€ ์œ ์ €๊ฐ€ ๋™์ผํ•œ ์•Œ๋ฆผ ์ŠคํŠธ๋ฆผ์„ ์—ฌ๋Ÿฌ ๊ฐœ๋กœ ๋ฐ›์•„๊ฐ€๊ณ  ์žˆ๋Š” ์ƒํƒœ

์ด ๊ตฌ์กฐ๋ฅผ ๊ทธ๋Œ€๋กœ ๋‘๋ฉด:

  • ์„œ๋ฒ„๋Š” ๊ฐ™์€ ๋ฐ์ดํ„ฐ๋ฅผ ๊ฐ™์€ ์œ ์ €์—๊ฒŒ ์—ฌ๋Ÿฌ ๋ฒˆ ์ค‘๋ณต ์ „์†ก
  • ํด๋ผ์ด์–ธํŠธ๋„ ํ•„์š” ์ด์ƒ์œผ๋กœ ๋™์ผํ•œ ์ด๋ฒคํŠธ๋ฅผ ์—ฌ๋Ÿฌ ๋ฒˆ ์ฒ˜๋ฆฌ
  • SSE์˜ ์žฅ์ ์ธ “๊ฐ€๋ณ๊ณ  ๋‹จ์ˆœํ•œ ์‹ค์‹œ๊ฐ„ ์ŠคํŠธ๋ฆผ”์ด
    ์˜คํžˆ๋ ค ๊ตฌ์กฐ์ ์œผ๋กœ ๋ฌด๊ฑฐ์›Œ์ง€๋Š” ์ƒํ™ฉ์ด ๋œ๋‹ค.

๊ทธ๋ž˜์„œ ์ด ์‹œ์ ๋ถ€ํ„ฐ ๊ณ ๋ฏผ์€ ์ด๋ ‡๊ฒŒ ๋ฐ”๋€Œ์—ˆ๋‹ค.

“SSE ์—ฐ๊ฒฐ์„ ํƒญ๋งˆ๋‹ค ์—ด์ง€ ๋ง๊ณ , ๋ธŒ๋ผ์šฐ์ € ๋‹จ์—์„œ ํ•˜๋‚˜๋กœ ๊ณต์œ ํ•  ์ˆ˜๋Š” ์—†์„๊นŒ?”

 

์ด ๋‹ต์— ๋Œ€ํ•ด์„œ๋Š” ๋‹ค์Œ ๋ ˆํผ๋Ÿฐ์Šค๋ฅผ ํ†ตํ•ด์„œ ๋ŒํŒŒ๊ตฌ๋ฅผ ์ฐพ์„ ์ˆ˜ ์žˆ์—ˆ๋‹ค.

toss slash 24: N๊ฐœ์˜ ํƒญ, ๋‹จ ํ•˜๋‚˜์˜ websocket์™€ ํ”Œ๋ ‰์Šค ํŒ€์˜ ๋ชจ๋“  ํƒญ์— ํผ์ง€๋Š” ์‹ค์‹œ๊ฐ„ ์ด๋ฒคํŠธ, SSE 1๊ฐœ๋กœ ๋๋‚ด๋Š” ์ „๋žต ๊ธ€์„ ํ†ตํ•ด์„œ worker์˜ ์กด์žฌ๋ฅผ ํ†ตํ•ด ์ด๋ฅผ ํ•ด๊ฒฐํ•  ์ˆ˜ ์žˆ๋‹ค๋Š” ํžŒํŠธ๋ฅผ ์–ป์—ˆ๋‹ค.

 

toss slash24 : N๊ฐœ์˜ ํƒญ, ๋‹จ ํ•˜๋‚˜์˜ ์›น์†Œ์ผ“ ์žฅํ‘œ ๋ฐœ์ทŒ

 

๋‘ ๊ธ€์˜ ๊ณตํ†ต๋œ ํ•ต์‹ฌ์€,Worker๋ฅผ ํ—ˆ๋ธŒ๋กœ ๋‘๊ณ  ์‹ค์‹œ๊ฐ„ ์—ฐ๊ฒฐ์„ ํ•˜๋‚˜๋กœ ์ˆ˜๋ ด์‹œํ‚จ๋‹ค๋Š” ์ „๋žต์ด์—ˆ๋‹ค.


โœ… Service Worker๊ฐ€ ์•„๋‹Œ, Shared Worker๋ฅผ ์„ ํƒํ•œ ์ด์œ 

Worker๋ฅผ ์‚ฌ์šฉํ•œ๋‹ค๋Š” ๋ฐฉํ–ฅ์„ฑ์€ ์žกํ˜”์ง€๋งŒ, ๋‹ค์Œ ์„ ํƒ์ง€๋Š” Service Worker vs Shared Worker์˜€๋‹ค.

Service Worker๋Š”:

  • ์บ์‹ฑ, ๋„คํŠธ์›Œํฌ ์ธํ„ฐ์…‰ํŠธ, ํ‘ธ์‹œ ์•Œ๋ฆผ ๋“ฑ
  • ์•ฑ ์ „์ฒด๋ฅผ ๋Œ€ํ‘œํ•˜๋Š” ๋ฐฑ๊ทธ๋ผ์šด๋“œ ๊ตฌ์กฐ์— ๊ฐ€๊น๋‹ค.

๋ฐ˜๋ฉด ๋‚ด๊ฐ€ ๋งŒ๋“ค๊ณ ์ž ํ–ˆ๋˜ ๊ตฌ์กฐ๋Š”:

  • ์ง€๊ธˆ ์—ด๋ ค ์žˆ๋Š” ํƒญ๋“ค๋ผ๋ฆฌ๋งŒ
  • SSE ํ•˜๋‚˜๋ฅผ ๊ณต์œ ํ•˜๋Š” ์‹ค์‹œ๊ฐ„ ํ—ˆ๋ธŒ

์ด ์„ฑ๊ฒฉ์—๋Š” Shared Worker๊ฐ€ ํ›จ์”ฌ ์ž˜ ๋งž์•˜๋‹ค.

Shared Worker๋Š”:

  • ์—ฌ๋Ÿฌ ํƒญ์ด ํ•˜๋‚˜์˜ ์›Œ์ปค๋ฅผ ๊ณต์œ ํ•  ์ˆ˜ ์žˆ๊ณ 
  • ๊ทธ ์•ˆ์—์„œ SSE ์—ฐ๊ฒฐ์„ ๋‹จ ํ•˜๋‚˜๋งŒ ์œ ์ง€ํ•  ์ˆ˜ ์žˆ์œผ๋ฉฐ
  • ๋ชจ๋“  ํƒญ์ด ๋‹ซํžˆ๋ฉด ์›Œ์ปค๋„ ์ž์—ฐ์Šค๋Ÿฝ๊ฒŒ ์ข…๋ฃŒ๋œ๋‹ค.

์ฆ‰, ์‹ค์‹œ๊ฐ„ ์•Œ๋ฆผ ์ „์šฉ ํ—ˆ๋ธŒ ์—ญํ• ์—๋Š” Service Worker๋ณด๋‹ค Shared Worker๊ฐ€ ๋” ์ ์ ˆํ•œ ์„ ํƒ์ง€์˜€๋‹ค.

๊ทธ๋ž˜์„œ ์ด ์‹œ์ ์—์„œ ๋ฐฉํ–ฅ์€ ๋ช…ํ™•ํ•ด์กŒ๋‹ค.

“SSE๋Š” Shared Worker ์•ˆ์—์„œ ํ•˜๋‚˜๋งŒ ์—ด๊ณ , ๊ฐ ํƒญ์€ ๊ทธ ๊ฒฐ๊ณผ๋ฅผ ๋ฐ›์•„์„œ ๋ณด์—ฌ์ฃผ์ž.”


โœ… ๋‹ค๋งŒ, Shared Worker๋Š” ‘๋งŒ๋Šฅ ํ•ด๊ฒฐ์ฑ…’์€ ์•„๋‹ˆ์—ˆ๋‹ค

Shared Worker๋Š” ๊ตฌ์กฐ์ ์œผ๋กœ๋Š” ์™„๋ฒฝํ•ด ๋ณด์˜€์ง€๋งŒ, ์‹ค์ œ ๋„์ž…์„ ๊ณ ๋ คํ•˜๋ฉด์„œ ๋ช‡ ๊ฐ€์ง€ ํ˜„์‹ค์ ์ธ ์ œ์•ฝ๋„ ํ•จ๊ป˜ ๋งˆ์ฃผํ•˜๊ฒŒ ๋˜์—ˆ๋‹ค.

  • ๋ชจ๋ฐ”์ผ ๋ธŒ๋ผ์šฐ์ €์—์„œ๋Š” ์ง€์›์ด ์ œํ•œ์ ์ด๊ณ 
  • public ๊ฒฝ๋กœ์˜ ์ˆœ์ˆ˜ .js ํŒŒ์ผ์—์„œ ๋กœ๋“œ๋˜์–ด์•ผ ํ•˜๋ฉฐ
  • ๋ฒˆ๋“ค๋ง, ๋ชจ๋“ˆ import, ๋””๋ฒ„๊น… ๋ฐฉ์‹๋„ ๊ธฐ์กด๊ณผ๋Š” ์ „ํ˜€ ๋‹ฌ๋ž๋‹ค

๊ทธ๋Ÿผ์—๋„ ๋ถˆ๊ตฌํ•˜๊ณ ,“SSE ์—ฐ๊ฒฐ์„ ์‚ฌ์šฉ์ž ๊ธฐ์ค€์œผ๋กœ ํ•˜๋‚˜๋งŒ ์œ ์ง€ํ•œ๋‹ค”๋Š” ๋ชฉํ‘œ๋ฅผ ๊ฐ€์žฅ ์ •ํ™•ํ•˜๊ฒŒ ๋‹ฌ์„ฑํ•  ์ˆ˜ ์žˆ๋Š” ์ˆ˜๋‹จ์€ ์—ฌ์ „ํžˆ Shared Worker๋ฟ์ด์—ˆ๋‹ค.

 

โ“Broadcasting Channel๋กœ๋„ ํ•ด๊ฒฐํ•  ์ˆ˜ ์žˆ์ง€ ์•Š์„๊นŒ?

ํ•œํŽธ์œผ๋กœ๋Š” ์ด๋Ÿฐ ์ƒ๊ฐ๋„ ์ž์—ฐ์Šค๋Ÿฝ๊ฒŒ ๋“ค์—ˆ๋‹ค.

“Broadcasting Channel์„ ํ†ตํ•ด ์ฑ„๋„์„ ํ•˜๋‚˜๋งŒ ์—ด๊ณ , ๋ฆฌ๋” ํƒญ์—์„œ ๋‹ค๋ฅธ ํƒญ์œผ๋กœ ์‹ค์‹œ๊ฐ„ ์ด๋ฒคํŠธ ์•Œ๋ฆผ์„ ๋™๊ธฐํ™”ํ•˜๋ฉด ๋˜์ง€ ์•Š์„๊นŒ?”

์ด ๋ฐฉ์‹ ์—ญ์‹œ ์ด๋ก ์ ์œผ๋กœ๋Š” ๊ฐ€๋Šฅํ•˜๋‹ค. ํŠน์ • ํƒญ์„ ๋ฆฌ๋” ํƒญ์œผ๋กœ ์‚ผ์•„ ๊ทธ ํƒญ์—์„œ๋งŒ SSE๋ฅผ ์—ด๊ณ ,์ˆ˜์‹ ํ•œ ์ด๋ฒคํŠธ๋ฅผ Broadcasting Channel์„ ํ†ตํ•ด ๋‹ค๋ฅธ ํƒญ์œผ๋กœ ์ „ํŒŒํ•˜๋Š” ๋ฐฉ์‹์ด๋‹ค.

 

ํ•˜์ง€๋งŒ ์ด ๊ตฌ์กฐ๋Š” ๋ช…ํ™•ํ•œ ๋‹จ์ ์„ ๊ฐ€์ง€๊ณ  ์žˆ์—ˆ๋‹ค.

  • ๋ฆฌ๋” ํƒญ์ด ๋‹ซํžˆ๋Š” ์ˆœ๊ฐ„ SSE ์—ฐ๊ฒฐ์ด ํ•จ๊ป˜ ๋Š๊ธฐ๊ณ 
  • ๊ทธ ์ฆ‰์‹œ ์ƒˆ๋กœ์šด ๋ฆฌ๋” ํƒญ์„ ์„ ์ถœํ•˜๋Š” ๋กœ์ง์ด ์ถ”๊ฐ€๋กœ ํ•„์š”ํ•ด์ง„๋‹ค
  • ๊ฒฐ๊ณผ์ ์œผ๋กœ ๊ตฌ์กฐ๊ฐ€ ๋‹จ์ˆœํ•ด์ง€๊ธฐ๋ณด๋‹ค๋Š” ์˜คํžˆ๋ ค ๋” ๋ณต์žกํ•ด์งˆ ๊ฐ€๋Šฅ์„ฑ์ด ์ปธ๋‹ค

์ฆ‰,“ํ•ญ์ƒ ํ•˜๋‚˜์˜ ์ฑ„๋„์„ ์œ ์ง€ํ•œ๋‹ค”๋Š” ๋ชฉํ‘œ๋ฅผ ์•ˆ์ •์ ์œผ๋กœ ๋‹ฌ์„ฑํ•˜๊ธฐ์—๋Š”, Broadcasting Channel ๊ธฐ๋ฐ˜ ๊ตฌ์กฐ๋Š” ๋ถˆํ™•์ •์„ฑ์ด ํฐ ์„ ํƒ์ง€๋ผ๊ณ  ํŒ๋‹จํ•˜๊ฒŒ ๋˜์—ˆ๋‹ค.

 

๊ทธ๋ž˜์„œ ๋‚˜๋Š” ๊ฒฐ๊ตญ ์ด ์‹œ์ ์—์„œ ์ด๋ ‡๊ฒŒ ๊ฒฐ์ •์„ ๋‚ด๋ฆฌ๊ฒŒ ๋œ๋‹ค.

“PC ํ™˜๊ฒฝ์—์„œ๋Š” Shared Worker๋กœ ๋‹จ์ผ SSE ์ฑ„๋„์„ ๊ตฌ์„ฑํ•˜๊ณ , ์ง€์›ํ•˜์ง€ ์•Š๋Š” ํ™˜๊ฒฝ์—์„œ๋Š” ๊ธฐ์กด SSE ๋ฐฉ์‹์œผ๋กœ fallback ์ฒ˜๋ฆฌํ•˜์ž.”

 

 

์ตœ์ข… ์•„ํ‚คํ…์ฒ˜: Shared Worker + Fallback ์ด์ค‘ ๊ตฌ์กฐ

์ขŒ : shared worker, ์šฐ: fall back

์•ž์„  ๊ณ ๋ฏผ๊ณผ ์„ ํƒ์„ ๋ฐ”ํƒ•์œผ๋กœ,
์‹ค์‹œ๊ฐ„ ์•Œ๋ฆผ ์‹œ์Šคํ…œ์˜ ์ตœ์ข… ์•„ํ‚คํ…์ฒ˜๋Š” Shared Worker ๊ธฐ๋ฐ˜ + Fallback ๊ตฌ์กฐ๋กœ ์ •๋ฆฌ๋˜์—ˆ๋‹ค.

ํ•ต์‹ฌ ์ „์ œ๋Š” ๋‹ค์Œ๊ณผ ๊ฐ™๋‹ค.

  • PC ํ™˜๊ฒฝ → Shared Worker๋ฅผ ํ†ตํ•ด SSE ์—ฐ๊ฒฐ 1๊ฐœ๋งŒ ์œ ์ง€
  • Shared Worker ๋ฏธ์ง€์› ํ™˜๊ฒฝ(๋ชจ๋ฐ”์ผ ๋“ฑ) → ๊ธฐ์กด ๋ฐฉ์‹๋Œ€๋กœ ํƒญ๋งˆ๋‹ค SSE ์ง์ ‘ ์—ฐ๊ฒฐ

์ด๋ ‡๊ฒŒ ์ด์ค‘ ๊ตฌ์กฐ๋ฅผ ๊ฐ€์ ธ๊ฐ€๋ฉด:

  • ์„ฑ๋Šฅ๊ณผ ๋น„์šฉ์ด ์ค‘์š”ํ•œ PC ํ™˜๊ฒฝ์—์„œ๋Š” ๊ฐ€์žฅ ์ด์ƒ์ ์ธ ๊ตฌ์กฐ
  • ํ˜ธํ™˜์„ฑ์ด ์ค‘์š”ํ•œ ๋ชจ๋ฐ”์ผ ํ™˜๊ฒฝ์—์„œ๋Š” ์•ˆ์ •์„ฑ์ด ์šฐ์„ ์ธ ๊ตฌ์กฐ

๋ฅผ ๋™์‹œ์— ๋งŒ์กฑ์‹œํ‚ฌ ์ˆ˜ ์žˆ์—ˆ๋‹ค.


Shared Worker๊ฐ€ ๋™์ž‘ํ•˜๋Š” ํ๋ฆ„

Shared Worker ๊ธฐ๋ฐ˜ ๊ตฌ์กฐ์˜ ๋™์ž‘ ํ๋ฆ„์€ ๋‹ค์Œ๊ณผ ๊ฐ™๋‹ค.

  1. ๋ธŒ๋ผ์šฐ์ €์˜ ์—ฌ๋Ÿฌ ํƒญ์—์„œ useEventSSE ํ›…์ด ์‹คํ–‰๋œ๋‹ค.
  2. ๊ฐ ํƒญ์€ Shared Worker์— ์—ฐ๊ฒฐํ•˜๊ณ , MessagePort๋ฅผ ํ†ตํ•ด ํ†ต์‹ ํ•œ๋‹ค.
  3. Shared Worker ๋‚ด๋ถ€์—์„œ๋Š” ๋‹จ ํ•˜๋‚˜์˜ SSE ์—ฐ๊ฒฐ๋งŒ ์ƒ์„ฑ๋œ๋‹ค.
  4. ์„œ๋ฒ„์—์„œ ์‹ค์‹œ๊ฐ„ ์ด๋ฒคํŠธ๊ฐ€ ๋„์ฐฉํ•˜๋ฉด,
  5. Shared Worker๊ฐ€ ๊ทธ ์ด๋ฒคํŠธ๋ฅผ ๋ชจ๋“  ํƒญ์œผ๋กœ ๋ธŒ๋กœ๋“œ์บ์ŠคํŠธํ•œ๋‹ค.
  6. ๊ฐ ํƒญ์€ ์ „๋‹ฌ๋ฐ›์€ ์ด๋ฒคํŠธ๋ฅผ ๊ทธ๋Œ€๋กœ UI์— ๋ฐ˜์˜ํ•œ๋‹ค.

์ด ๊ตฌ์กฐ๋ฅผ ํ†ตํ•ด
๋ธŒ๋ผ์šฐ์ € ํƒญ ์ˆ˜์™€ ์ƒ๊ด€์—†์ด SSE ์—ฐ๊ฒฐ์€ ํ•ญ์ƒ 1๊ฐœ๋กœ ์œ ์ง€๋œ๋‹ค.


Shared Worker ๋ฏธ์ง€์› ํ™˜๊ฒฝ์˜ Fallback ๊ตฌ์กฐ

๋ฐ˜๋ฉด Shared Worker๋ฅผ ์‚ฌ์šฉํ•  ์ˆ˜ ์—†๋Š” ํ™˜๊ฒฝ์—์„œ๋Š”
์ดˆ๊ธฐ ์„ค๊ณ„๋Œ€๋กœ ๋‹จ์ˆœํ•œ ๊ตฌ์กฐ๋ฅผ ์œ ์ง€ํ•˜๋„๋ก ํ–ˆ๋‹ค.

  • ๊ฐ ํƒญ์ด /api/sse/event๋กœ ์ง์ ‘ SSE ์—ฐ๊ฒฐ
  • ์ด๋ฒคํŠธ๋Š” ๊ฐœ๋ณ„ ํƒญ์—์„œ ๋ฐ”๋กœ ์ฒ˜๋ฆฌ
  • ๋ณ„๋„์˜ ๋ธŒ๋กœ๋“œ์บ์ŠคํŠธ๋‚˜ ํ—ˆ๋ธŒ ๋ ˆ์ด์–ด๋Š” ๋‘์ง€ ์•Š์Œ

์ด ๋ฐฉ์‹์€ ์—ฐ๊ฒฐ ์ˆ˜๋Š” ๋Š˜์–ด๋‚˜์ง€๋งŒ, ์ง€์› ๋ฒ”์œ„์™€ ์•ˆ์ •์„ฑ ๋ฉด์—์„œ๋Š” ๊ฐ€์žฅ ํ™•์‹คํ•œ ์„ ํƒ์ง€์ด๊ธฐ๋„ ํ•˜๋‹ค.

์ฆ‰, ์ด ์•„ํ‚คํ…์ฒ˜๋Š” ์ฒ˜์Œ๋ถ€ํ„ฐ “์ตœ์ ํ™”๋œ ๊ตฌ์กฐ + ์–ธ์ œ๋“  fallback ๊ฐ€๋Šฅํ•œ ๊ตฌ์กฐ”๋ฅผ ํ•จ๊ป˜ ๊ฐ–๋„๋ก ์„ค๊ณ„๋œ ํ˜•ํƒœ๋ผ๊ณ  ๋ณผ ์ˆ˜ ์žˆ๋‹ค.


์ด ๊ตฌ์กฐ์˜ ํ•ต์‹ฌ ์š”์•ฝ

์ •๋ฆฌํ•˜๋ฉด, ์ตœ์ข… ๊ตฌ์กฐ์˜ ํ•ต์‹ฌ์€ ๋”ฑ ์„ธ ๊ฐ€์ง€๋‹ค.

  1. SSE๋Š” ์‚ฌ์šฉ์ž ๊ธฐ์ค€์œผ๋กœ 1๊ฐœ๋งŒ ์œ ์ง€ํ•˜๋Š” ๊ฒƒ์„ ๋ชฉํ‘œ๋กœ ํ•œ๋‹ค
  2. PC ํ™˜๊ฒฝ์—์„œ๋Š” Shared Worker๊ฐ€ ๊ทธ ์—ญํ• ์„ ๋‹ด๋‹นํ•œ๋‹ค
  3. Shared Worker ๋ฏธ์ง€์› ํ™˜๊ฒฝ์—์„œ๋Š” ๊ธฐ์กด SSE ๋ฐฉ์‹์œผ๋กœ ์•ˆ์ „ํ•˜๊ฒŒ fallback ํ•œ๋‹ค

์ด์ œ ์‹ค์‹œ๊ฐ„ ์•Œ๋ฆผ์€:

  • ๋ธŒ๋ผ์šฐ์ € ํƒญ์ด ๋ช‡ ๊ฐœ๋“ 
  • ์ธ์ฆ๊ณผ ์‹ค์‹œ๊ฐ„์„ฑ์€ ์œ ์ง€ํ•˜๋ฉด์„œ
  • ์„œ๋ฒ„์™€์˜ ์—ฐ๊ฒฐ ์ˆ˜๋Š” ์ตœ์†Œํ™”ํ•˜๋Š” ๊ตฌ์กฐ๋กœ ๋™์ž‘ํ•˜๊ฒŒ ๋˜์—ˆ๋‹ค.

๋Œ“๊ธ€