MVC 패턴을 적용한 express 서버를 구현해보자.
MVC 패턴
모델-뷰-컨트롤러 (Model-View-Controller, MVC) 는 소프트웨어 디자인 패턴입니다.
비즈니스 로직을 분리해 서로 영향없이 유지보수할 수 있는 애플리케이션을 만들 수 있습니다.
- Model : 데이터 관련 작업 담당
- View : 사용자 인터페이스 담당
- Controller : 데이터 (Model)과 사용자 인터페이스 (View) 요소 연결 담당
View 설정 (+ ejs)
먼저 ejs 모듈을 설치하고 app.js
에 view engine을 설정합니다.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
import express from "express";
import path from "path";
import bodyParser from "body-parser";
const app = express();
const __dirname = path.resolve();
// 정적 파일
app.use("/", express.static(`${__dirname}/src/public`));
// 앱 세팅
app.set("views", "./src/views");
app.set("view engine", "ejs");
// 미들웨어
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: true }));
// 3000 포트로 서버 오픈
app.listen(3000, () => {
console.log("express server on port 3000");
});
test 파일 만들기
views 폴더안에 간단한 test.ejs
파일을 만듭니다.
1
2
3
4
5
6
7
8
9
10
11
12
13
<!-- test.ejs -->
<!DOCTYPE html>
<html lang="ko">
<head>
<meta charset="UTF-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Root</title>
</head>
<body>
Hello World!
</body>
</html>
Router 설정
Router는 특정 주소로 요청이 들어오면 주소와 HTTP method 별로 Controller와 연결하는 역활을합니다.
또한, 요청과 함께 받은 데이터들의 유효성 검사 등도 Router에서 담당합니다.
Routes 폴더를 만들고 route_test.js
파일을 만들어 express router를 작성합니다.
1
2
3
4
5
6
7
8
9
10
import express from "express";
import ctrl from "../controller/controller-test.js";
const Router = express.Router();
Router.get("/", ctrl.output.test);
Router.get("/test", ctrl.process.test);
export default Router;
서버 파일인 app.js
와 라우터 파일 route_test.js
파일을 미들웨어로 연결합니다.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
import express from "express";
import path from "path";
import bodyParser from "body-parser";
import testRouter from "./src/routes/route_test.js";
const app = express();
const __dirname = path.resolve();
// 정적 파일
app.use("/", express.static(`${__dirname}/src/public`));
// 앱 세팅
app.set("views", "./src/views");
app.set("view engine", "ejs");
// 미들웨어
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: true }));
// router
app.use("/", testRouter);
// 3000 포트로 서버 오픈
app.listen(3000, () => {
console.log("express server on port 3000");
});
Controller 설정
Controller는 요청을 처리하고 응답하는 역할을 합니다.
Model과 View 간의 중간 다리 역할로 필요에따라 Model과 소통하여 받은 데이터를 View(클라이언트)로 응답합니다.
controllers 폴더를 만들고 controller_test.js
파일에 output, process 객체로 나누어 작성하겠습니다.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
import model_test from "../models/model_test.js";
const output = {
test: (req, res) => {
res.render("test");
},
};
const process = {
test: async (req, res) => {
const data = await model_test.getUsers();
res.send(data);
},
};
export default { output, process };
Models 설정
Model은 Controller로 부터 요청을 받아 DB에 접근해 CRUD 로직을 처리합니다.
mysql2 모듈의 createPool을 활용해보겠습니다.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
import mysql from "mysql2/promise";
const pool = await mysql.createPool({
host: process.env.DB_HOST, //실제로 연결할 데이터베이스의 위치
user: process.env.DB_USER,
password: process.env.DB_PASSWORD,
database: "user", //데이터베이스 이름
port: 3306,
connectionLimit: 30,
});
const conn = await pool.getConnection(async (conn) => conn);
class userStorage {
static async getUsers() {
try {
const [rows] = await conn.query("SELECT * FROM users");
return rows;
} catch (err) {
console.log(err);
} finally {
conn.release();
}
}
}
export default userStorage;
TEST
서버를 열고 잘 동작 하는 지 확인해보겠습니다
먼저 서버를 실행합니다.
localhost:3000 주소로 접속해봅니다.
localhost:3000/test 주소로 접속해보겠습니다.
결론
MVC 패턴의 틀을 잡았으니 다음 포스트에서 추가로 기능을 구현해보겠습니다.
먼저 간단하게 로그인 기능을 구현해보겠습니다.