본문 바로가기
C++ 200제/코딩 IT 정보

Node js + Express에서 MVC 같이 써보기 - 라우터 예제

by vicddory 2020. 3. 11.


이번엔 제목 그대로 "Node.js + 익스프레스" 환경에서 MVC 함께 써보려고 합니다.


처음 Express framework를 다룰 때, 대부분의 코드를 router에 직접 코딩했었는데요. 어떻게 해야 더 이쁘게 코딩할 수 있을까 고민한 것이 계기입니다.


원래 MVC 모델

응용 프로그램(애플리케이션)을 M (Model) V (View) C (Controller) 3개로 분할하여 구축하는 개발 방법론입니다.


  • Model : 응용 프로그램 데이터, 비즈니스 규칙, 논리 함수, 로직
  • View : 그래프, 그림 등 임의의 (임시) 정보 표현
  • Controller : 입력을 받아 model과 view 명령으로 변환

익스프레스

Express는 웹 및 모바일 애플리케이션을 위한 일련의 강력한 기능을 제공하는 간결하고 유연한 Node.js 웹 애플리케이션 프레임워크입니다.


위에서 설명한 대로, Express framework는 어디까지나 최소한의 기능만 제공하므로 모듈을 적절히 조합하면, 굉장히 유연하게 결과물을 만들어 낼 수 있습니다.


잘 보면서 따라 하기

var express = require('express');
var router  = express.Router();
var mysql   = require('mysql');
var db      = require('../config/db');

router.get('/users/index', (reqresnext=> {

  var sql = 'select * from users';

  try {
    const connection = mysql.createConnection(db);
    connection.connect();
    connection.query(sql,
      (errorresultsfields=> {
        if (error == null) {
          res.render('index.ejs',
          {
            contentresults
          });
        }else{
          throw(error);
        }
      }
    );
    connection.end();
  } catch(e) {
    res.render('index.ejs',
    {
      content: {errore},
    });
  }
});


Express framework에서 작성된 코드를 검토할 때 흔히 볼 수 있는 형태입니다. 주로 이런 느낌의 코드를 자주 접하게 됩니다.


당연히 위의 코드도 실행에 문제는 없습니다만, 양이 많아지면 코드의 질은 장담할 수 없다고 생각합니다.


다른 언어로 MVC 프레임워크 이용한 개발한 분들에게도 위화감이 드는 코드일 겁니다.


하고 싶은 일

익스프레스(Express)를 소위 MVC 프레임워크 스럽게 사용하고 싶어요.


해봐요

빨리 시작해 볼게요. 사용자 정보를 표시하는 페이지를 예로 들어 코드를 작성해 봅니다.


전제 사항

  • Node.js 버전 : 10.15.1
  • Express 버전 : 4.16.0
  • 데이터베이스 : MySQL 5.7


디렉터리 구성

├── app.js
├── bin
│   └── www
├── config
│   └── db.js
├── controllers
│   └── UserController.js
├── models
│   └── Users.js
├── views
│   └── index.ejs
├── routes
│   └── routes.js
├── package.json
├── public


express-generator를 구축하고,


  • config
  • controllers
  • models


들을 추가합니다.

라우팅 설정

routes / routes.js

var express = require('express');
var router = express.Router();
var userController = require('../controllers/UserController')

router.get('/users'userController.doGetUser);
router.post('/users/regist'userController.doRegistUser);

module.exports = router;


라우팅은 routes.js 파일에 작성합니다.


HTTP 요청(리퀘스트 request)의 엔드포인트(end point)를 어떤 모듈에서 처리할지 작성되어 있습니다.


node.js 예제 소스 중, 세 번째 줄에서 이른바 controller를 읽습니다.


Controller 작성

controllers / UserController.js

const express = require('express');
const Users = require('../models/Users');
const Views = '../views/'

module.exports = {
  doGetUserfunction (reqresnext) {
    Users.getUser(id).then((result=> {
      res.render(Views + 'index.ejs',{usersresult});
    });
  }
}


Controller는 router에서 받은 요청(request)에 대해 Model 작업을 수행하고 결과를 View에 전달합니다.


두 번째 줄에서 Model을 읽고 있습니다.


Model 작성

models / User.js

const mysql = require('mysql');
const db = require('../config/db');
const table = 'users';

module.exports = {

  getUserfunction () {
    return new Promise ((resolvereject=> {
      const con = mysql.createConnection(db);
      con.query(
        `select id, name, date_format(birthdate,"%Y/%m/%d")
         as birthdate from ${table}`,  (errresultfields=>
          {
          if ( err ) {
            reject(err);
          } else {
            resolve(result);
          }
        });
      con.end();
    });
  },
}


Model은 DB에서 값을 가져와 Controller에 반환합니다.


View 작성

<table>
  <tbody>
    <th>No</th>
    <th>이름</th>    
    <th>생년월일</th>
    <% for( var i in users ){ %>
    <tr>
      <td><%= users[i].id %></td>
      <td><%= users[i].name %></td>
      <td><%= users[i].birthdate %></td>
    </tr>
    <% } %>
  </tbody>
</table>


Controller에서 받은 데이터를 사용하여 렌더링합니다.


정리

더 나은 작성 방법이 있을 거라고 생각하며, 위와 같이 MVC 모델을 적용할 수 있다고 생각합니다.


router에서 모든 처리 과정을 작성(코딩)할 때와 비교하면 매우 깔끔하며, 유지 보수도 쉬워질 것으로 예상합니다.


그렇다는 것은, 개인적으로 "Node.js + 익스프레스 framework에서 MVC 함께 써보기"는 충분히 유용하다는 것입니다.


그럼 또 만나요!



댓글