๐ŸŒณ๋ชฉํ‘œ

๋ผ์šฐํ„ฐ ๊ธฐ๋Šฅ์„ ๋งŒ๋“ค์–ด ๋‹ค์–‘ํ•œ ๊ฒฝ๋กœ๋ฅผ ์ฒ˜๋ฆฌํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

๊ธฐ์กด ๋ผ์šดํŒ…์˜ ํ•œ๊ณ„

์ง€๊ธˆ๊นŒ์ง€ ์šฐ๋ฆฌ๊ฐ€ ๋งŒ๋“  ์–ดํ”Œ๋ฆฌ์ผ€์ด์…˜์€ ์ •์ ํŒŒ์ผ์„ ์ œ์™ธํ•œ ๋ชจ๋“  ์š”์ฒญ์„ index ๋ฏธ๋“ค์›จ์–ด๊ฐ€ ์ฒ˜๋ฆฌํ•ฉ๋‹ˆ๋‹ค.

app.use(logger())
app.use(serveStatic())
app.use(index)
app.use(error404)
app.use(error)

โ€œGET /fooโ€ ๋กœ ์š”์ฒญํ•˜๋”๋ผ๋„ index ๋ฏธ๋“ค์›จ์–ด๊ฐ€ ๋™์ž‘ํ•ด์„œ index.html ํŒŒ์ผ์„ ์ œ๊ณตํ•˜๋Š” ๊ฒƒ์ด์ฃ . ์•„, ๋ฌผ๋ก  ์—๋Ÿฌ๊ฐ€ ๋ฐœ์ƒํ•˜๋ฉด ๋‹ค๋ฅด์ง€๋งŒ์š”.

๋งŒ์•ฝ ์•„๋ž˜์™€ ๊ฐ™์ด ์ฝ”๋”ฉํ•  ์ˆ˜ ์žˆ๋‹ค๋ฉด ์–ด๋–จ๊นŒ์š”?

app.use('/', indexController)
app.use('/foo', fooController)

ํŠน์ • ์ฃผ์†Œ(โ€œ/โ€)์˜ ์š”์ฒญ์ด ์žˆ์„ ๊ฒฝ์šฐ๋งŒ ์„ค์ •ํ•œ ๋ฏธ๋“ค์›จ์–ด(indexController)๋ฅผ ์‹คํ–‰ํ•˜๋„๋ก ํ•˜๋Š” ๋ฐฉ๋ฒ•์ž…๋‹ˆ๋‹ค. ๋ฌผ๋ก  โ€œ/fooโ€ ๊ฒฝ๋กœ๋กœ ์š”์ฒญํ•˜๋ฉด fooController๊ฐ€ ๋™์ž‘๋Š” ๊ฑฐ์ง€์š”.

use() ๋ฉ”์†Œ๋“œ์— ๋ผ์šฐํ„ฐ ๊ธฐ๋Šฅ ์ถ”๊ฐ€

๋ฏธ๋“ค์›จ์–ด ๋“ฑ๋ก ํ•จ์ˆ˜์ธ use๋ฅผ ์กฐ๊ธˆ ํ™•์žฅํ•ด ๋ณด๊ฒ ์Šต๋‹ˆ๋‹ค. ๊ฒฝ๋กœ๊นŒ์ง€ ์ธ์ž๋กœ ์ถ”๊ฐ€ํ•ด ๋ณผ๊นŒ์š”? ๋ฏธ๋“ค์›จ์–ด๋ฅผ ์‹คํ–‰ํ•  ๋•Œ ๋“ฑ๋กํ•œ ๊ฒฝ๋กœ์™€ ์ง€๊ธˆ ๋“ค์–ด์˜จ ์š”์ฒญ ์ฃผ์†Œ๊ฐ€ ์ผ์น˜ํ•  ๋•Œ๋งŒ ๊ทธ ๋ฏธ๋“ค์›จ์–ด ํ•จ์ˆ˜๋ฅผ ์‹คํ–‰ํ•˜๋„๋ก ํ•˜๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค.

๐Ÿค์‹ค์Šต - ๋ผ์šฐํ„ฐ ๊ธฐ๋Šฅ ๊ตฌํ˜„

๋จผ์ € ์ง€๋‚œ ์‹œ๊ฐ„๊นŒ์ง€ ์ž‘์„ฑํ•œ ์ฝ”๋“œ๋กœ ์ด๋™ํ•ฉ๋‹ˆ๋‹ค.

$ git checkout -f module/logger-color

app.use(path, fn)์œผ๋กœ ๋ฉ”์†Œ๋“œ๋ฅผ ํ™•์žฅํ•ด ๋ณด์„ธ์š”.

ํžŒํŠธ: fn._path์— path๋ฅผ ์ €์žฅ

๐Ÿค ํ’€์ด

๊ฐ™์ด ํ’€์ด ๋ณด์ฃ . use() ๋ฉ”์†Œ๋“œ๊ฐ€ ์ •์˜๋œ src/Application.js ํŒŒ์ผ์„ ๋จผ์ € ์ˆ˜์ •ํ•ฉ๋‹ˆ๋‹ค.

const use = (path, fn) => {
  if (typeof path === 'string' && typeof fn === 'function') {
    fn._path = path;
  } else if (typeof path == 'function') {
    fn = path;
  } else {
    throw Error('Usage: use(path, fn) or use(fn)');
  }

  _middleware.add(fn);
}

path ์ธ์ž๋Š” ์„ ํƒ์‚ฌํ•ญ์ด๊ธฐ ๋•Œ๋ฌธ์— ์ด ๋ถ€๋ถ„์„ ์œ ์—ฐํ•˜๊ฒŒ ์ฒ˜๋ฆฌํ•ด ์ฃผ์–ด์•ผ ํ•˜๋Š”๋ฐ if/else ๊ตฌ๋ฌธ์ด ๊ทธ ์ฝ”๋“œ์ž…๋‹ˆ๋‹ค.

์ค‘์š”ํ•œ ๊ฒƒ์€ ๋‘๋ฒˆ์งธ ๋ฏธ๋“ค์›จ์–ด ์ธ์ž fn์˜ _path ์†์„ฑ์— ๊ฒฝ๋กœ๋ฅผ ์ €์žฅํ•œ ๋ถ€๋ถ„์ž…๋‹ˆ๋‹ค. ์ด ํ›„ ๋ฏธ๋“ค์›จ์–ด๋ฅผ ์‹คํ–‰ํ•  ๋•Œ ์ด ๋ฌธ์ž์—ด๊ณผ ์š”์ฒญURL๋ฅผ ๋น„๊ตํ•œ ๋’ค ํ•จ์ˆ˜๋ฅผ ์‹คํ–‰ํ•  ๊ฒƒ์ด ๊ฑฐ๋“ ์š”. ์ฐธ๊ณ ๋กœ ์ž๋ฐ”์Šคํฌ๋ฆฝํŠธ ํ•จ์ˆ˜๋Š” ์ด๋ ‡๊ฒŒ ๊ฐ์ฒด ํ˜•์‹์œผ๋กœ ํ”„๋Ÿฌํผํ‹ฐ๋ฅผ ์ถ”๊ฐ€ ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

์ด์ œ run() ๋ฉ”์†Œ๋“œ๊ฐ€ ์ •์˜๋œ src/Middleware.js ํŒŒ์ผ๋กœ ์ด๋™ํ•˜๊ฒ ์Šต๋‹ˆ๋‹ค.

const _run = (i, err) => {
  // ...
  
  if (nextMw._path) { // ๊ฒฝ๋กœ๋ฅผ ๋น„๊ตํ•œ๋‹ค 
    const pathMatched = _req.url === nextMw._path;
    return pathMatched ? nextMw(_req, _res, next) : _run(i + 1)
  }

  nextMw(_req, _res, next);
}

use() ๋ฉ”์†Œ๋“œ์—์„œ ์ €์žฅํ•œ ๊ฒฝ๋กœ์ •๋ณด๋Š” nextMw._path๋ฅผ ํ†ตํ•ด ์ ‘๊ทผํ• ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. ์‹ค์ œ ์š”์ฒญ URL(_req.url)๊ณผ ๋น„๊ตํ•ด์„œ ๊ฒฝ๋กœ๊ฐ€ ๊ฐ™์œผ๋ฉด ๋ฏธ๋“ค์›จ์–ด๋ฅผ ์‹คํ–‰ํ•ฉ๋‹ˆ๋‹ค. ๊ทธ๋ ‡์ง€ ์•Š์œผ๋ฉด ๋‹ค์Œ ๋ฏธ๋“ค์›จ์–ด๋ฅผ ์ฐพ๋Š” ๋ฐฉ์‹์ด์ฃ . (_run(i + 1))

๋ผ์šฐํ„ฐ ์‚ฌ์šฉ

app.js์— ์žˆ๋Š” index ๋ฏธ๋“ค์›จ์–ด์™€ error ๋ฏธ๋“ค์›จ์–ด๋ฅผ ๋ชจ๋“ˆ๋กœ ๋ถ„๋ฆฌํ•˜๊ฒ ์Šต๋‹ˆ๋‹ค.

๋จผ์ € routers/index.js ํŒŒ์ผ์— index ๋ฏธ๋“ค์›จ์–ด๋ฅผ ์˜ฎ๊น๋‹ˆ๋‹ค.

const path = require('path')
// ...

const listPosts = () => (req, res, next) => {
  const publicPath = path.join(__dirname, '../public');
  // ...
}

module.exports = {
  listPosts
}

ํฌ์ŠคํŠธ ๋ชฉ๋ก์„ ๋ณด์—ฌ์ค€๋‹ค๋Š” ์˜๋ฏธ์—์„œ listPosts ๋ผ๋Š” ์ด๋ฆ„์˜ ํ•จ์ˆ˜๋ฅผ ๋งŒ๋“ค์–ด ๋ชจ๋“ˆ๋กœ ๋…ธ์ถœํ•˜์˜€์Šต๋‹ˆ๋‹ค.

middlewares/errors.js์— error404, error ๋ฏธ๋“ค์›จ์–ด๋„ ์˜ฎ๊ธฐ๊ฒจ ๋ณด์ง€์š”.

const error404 = () => (req, res, next) => {
  // ...
}

const error = () => (err, req, res, next) => {
  // ...
}

module.exports = {
  error404,
  error,
}

๋งˆ์ง€๋ง‰์œผ๋กœ app.js ๊ฐ€ ์–ผ๋งˆ๋‚˜ ๋‹จ์ˆœํ•˜๊ฒŒ ๊ฐœ์„ ๋˜์—ˆ๋Š”์ง€ ํ™•์ธํ•ด ๋ด…์‹œ๋‹ค.

const serveStatic = require('./middlewares/serve-static');
const logger = require('./middlewares/logger');
const errors = require('./middlewares/errors');
const index = require('./routes/index');
const App = require('./src/Application');
const app = App();

app.use(logger());
app.use(serveStatic());
app.use('/', index.listPosts());
app.use(errors.error404());
app.use(errors.error());

module.exports = app;

Application ์ธ์Šคํ„ด์Šค๋ฅผ ๋งŒ๋“ค๊ณ  ์—ฌ๊ธฐ์— ๋ฏธ๋“ค์›จ์–ด๋ฅผ ์ถ”๊ฐ€ํ•˜๋Š” ์ฝ”๋“œ๋งŒ ๋“ค์–ด ์žˆ์ฃ . ์ด๊ฒƒ๋งŒ ๋ณด๋”๋ผ๋„ ์„œ๋ฒ„ ์–ดํ”Œ๋ฆฌ์ผ€์ด์…˜์ด ์–ด๋–ค ๋™์ž‘์„ ํ•˜๋Š”์ง€ ๊ฐ€๋Š ํ•  ์ˆ˜ ์žˆ์„ ๊ฒƒ ๊ฐ™์Šต๋‹ˆ๋‹ค.

๋ฟ๋งŒ์•„๋‹ˆ๋ผ ๊ธฐ๋Šฅ๋„ ๋ฏธ์„ธํ•˜๊ฒŒ ๋‹ฌ๋ผ ์ง‘๋‹ˆ๋‹ค. ์ด์   ์ œ๋Œ€๋กœ 404 ์‘๋‹ต์„ ํ•  ์ˆ˜ ์žˆ์ฃ .

๋งŒ์•ฝ ์ •์˜ ๋˜์ง€ ์•Š์€ ๊ฒฝ๋กœ, ๊ฐ€๋ น โ€œ/fooโ€๋กœ ์š”์ฒญ์„ ํ•œ๋‹ค๊ณ  ํ•ฉ์‹œ๋‹ค. ์„œ๋ฒ„์—์„œ๋Š” logger -> serveStatic ๋ฏธ๋“ค์›จ์–ด๊นŒ์ง€ ๊ฐ€๋‹ค๊ฐ€ index.listPost๋Š” ๊ฑด๋„ˆ ๋›ฐ์–ด ๋ฒ„๋ฆฌ๊ฒ ์ฃ . ๊ฒฝ๋กœ๊ฐ€ ๋งž์ง€ ์•Š์œผ๋‹ˆ๊น์š”. erros.error404 ๋ฏธ๋“ค์›จ์–ด๋ฅผ ๋งŒ๋‚˜๊ฒŒ ๋˜๊ณ  ๋น„๋กœ Not Found ๋ฌธ์ž์—ด์„ ์‘๋‹ตํ•˜๊ฒŒ ๋  ๊ฒƒ์ž…๋‹ˆ๋‹ค.

์ •๋ฆฌ

  • ๊ฒฝ๋กœ์— ๋”ฐ๋ผ ์ปจํŠธ๋กค๋Ÿฌ๋ฅผ ์„ค์ •ํ•˜๋Š” use() ๋ฉ”์†Œ๋“œ๋ฅผ ๊ตฌํ˜„ํ–ˆ์Šต๋‹ˆ๋‹ค.
  • ์–ดํ”Œ๋ฆฌ์ผ€์ด์…˜ ์ฝ”๋“œ๋ฅผ ๋‹จ์ˆœํ•˜๊ฒŒ ๊ฐœ์„ ํ•˜์˜€์Šต๋‹ˆ๋‹ค.

๋ชฉ์ฐจ ๋ฐ”๋กœ๊ฐ€๊ธฐ