본문 바로가기

[NodeJS] 웹 서버의 라우팅 처리 방법 - 02

2022.06.09. 오전 8:00
by 코드트리

이전 글에서 기본 Express.js를 사용하여 간단하게 웹 서버를 만들어보았다. 이번 글에서는 웹서버를 활용하여 라우팅 처리 방법에 대해 알아보기로 하자.

이번 글에서는..

  1. Node.js의 Express로 웹 서버 만들기

  2. 웹 서버의 라우팅 처리 방법

  3. Express에서 에러 처리와 정적 파일 제공하는 방법

  4. Json-server 구축 및 활용(방명록 만들기 소스제공)

라우팅이란?

Routing

라우팅이란 특정 엔드 포인트에 대한 클라이언트 요청에 서버가 응답하는 방법을 결정하는 것으로 이 챕터에서의 라우팅은 화면에서 다른 화면으로 전환하는 내비게이션 기능이라고 생각하면 이해가 쉬울 것이다.

<엔드 포인트>

URI (경로)와 HTTP 요청 메서드(GET, POST, PUT, DELETE 등)로 구분된 클라이언트 요청을 말한다.

여기서 설치한 Express에서의 라우트 구조를 살펴보자.

const express = require('express'); const app = express(); // 클라이언트에서 HTTP 요청 메소드 중 // GET을 이용해서 'host:port'로 요청을 보내면 // 실행되는 라우트 app.get('/', (req, res) => { res.send('Hello World!'); });

app.METHOD(PATH, HANDLER);

  • app : Express의 인스턴스

  • METHOD : HTTP 요청 메서드(GET, POST, PUT, DELETE 등)

  • PATH : 서버에서의 경로

  • HANDLER : 라우트(Route)가 일치할 때 실행되는 함수

라우트 메서드

클라이언트에서 서버로 요청을 보낼 때 사용한 HTTP 요청 메서드를 말한다.

예를 들어 설명해 보면,

클라이언트에서 get 을 사용해서 HTTP 요청 메서드를 서버로 전송했다면, Express 라우트 메서드 역시 get으로 작성된 처리 코드가 있어야 해당 함수가 동작 된다.

다음 예제 코드를 보면 이해가 좀 더 빠를 것 같다.

const express = require("express"); const app = express(); app.listen(3000, () => { // 3000번 포트로 웹 서버 실행 console.log("Server started. port 3000."); }); // 클라이언트에서 HTTP 요청 메소드 GET 방식으로 'host:3000/customer'를 호출했을 때 app.get("/customer", (req, res) => { res.send("get 요청에 대한 응답"); }); // 클라이언트에서 HTTP 요청 메소드 POST 방식으로 'host:3000/customer'를 호출했을 때 app.post("/customer", (req, res) => { res.send("post 요청에 대한 응답"); }); // 클라이언트에서 요청한 HTTP 요청 메소드 종류에 상관 없이 'host:3000/customer'를 호출했을 때 app.all("/customer", (req, res) => { res.send("모든 요청에 대한 응답"); });

라우트 경로

요청 메서드와의 조합을 통해서 요청이 이루어질 수 있는 엔드 포인트를 정의해 준다.

라우트를 표기하는 문자열, 패턴, 정규식의 예시를 알아보자.

문자열 예시

'/', '/about', '/about/customer'

문자열 패턴 예시

'/ab?cd' // 'b?'는 문자 'b'가 0개 혹은 1개 있다는 것을 의미 '/ab+cd' // 'b+'는 문자 'b'가 1개 이상 있다는 것을 의미 'ab*cd' // 문자'ab'와문자'cd'사이에문자가없거나혹은어떤문자도올수있다는것을의미 'ab(cd)?e' // '(cd)?'는 문자 'cd'가 0번 혹은 1번 있을 수 있다는 것을 의미

정규식 예시

/a/ // 클라이언트에서 요청한 라우트 경로에 'a'가 포함되어 있는 경우 /^insert/ // 클라이언트에서 요청한 라우트 경로가 문자 'insert'로 시작하는 경우

라우트 핸들러

클라이언트 요청에 따라 라우트가 일치할 경우 실행되는 콜백 함수를 말한다.

라우트 핸들러에서 사용되는 매개변수를 알아보자.

  • req : Request로 클라이언트의 요청 정보를 담고 있음

  • res : Response로 클라이언트에게 응답하기 위한 정보를 담고 있음

  • next : 다음 미들웨어 함수를 가리키는 Object

next Object 사용 예시

// 콜백 함수의 세 번째 매개변수로 next 오브젝트 사용 app.get('/example', (req, res, next) => { console.log('첫 번째 콜백 함수'); next(); // 다음 콜백 함수 호출 }, (req, res) => { res.send('두 번째 콜백 함수'); // 클라이언트로 응답 });

콜백 함수 배열 사용 예시

const ex0 = (req, res, next) => { console.log('첫 번째 콜백 함수'); next(); // 다음 콜백 함수 호출 }; const ex1 = (req, res, next) => { console.log("두 번째 콜백 함수"); next(); // 다음 콜백 함수 호출 }; const ex2 = (req, res, next) => { res.send("세 번째 콜백 함수"); // 클라이언트로 응답 }; app.get('/example', [ex0, ex1, ex2]); // 콜백 함수 배열로 정의

응답 메서드

다음 메서드 중에 한 가지 방법으로 응답해야 한다.

서버에서 응답하지 않은 경우에 클라이언트는 응답을 받지 못하고 정지된 상태를 유지한다.

응답 메서드

설명

res.download()

파일을 다운로드하도록 프롬프트

res.end()

응답 프로세스를 종료한다.

res.json()

JSON 응답을 전송한다.

res.jsonp()

JSONP 지원을 통해 JSON 응답을 전송한다.

res.redirect()

요청의 경로를 재지정해 준다.

res.render()

뷰(view) 템플릿을 렌더링 해준다.

res.send()

다양한 유형의 응답을 전송한다.

res.sendFile()

파일을 octet 스트림으로 전송한다.

res.sendStatus()

응답 상태 코드를 설정한 후 해당 코드를 응답 본문(body)에 담아서 전송한다.

(404 Not Found 등)

라우트 처리

app.route() : 모듈식 라우트를 작성하면 중복성이 감소해 효율적인 코드 관리가 가능하다.

app.route()

get, post, put과 같은 라우트 메서드를 한곳에 작성할 수 있다.

// 모듈식 라우터 - 하나의 라우트 경로로 각 라우트 메소드 처리 app.route('/customer') .get((req, res) => { // HTTP 메소드 GET 요청에 대한 조회 처리 res.send('고객 정보 조회'); }) .post((req, res) => { // HTTP 메소드 GET 요청에 대한 저장 처리 res.send('신규 고객 추가'); }) .put((req, res) => { // HTTP 메소드 GET 요청에 대한 수정 처리 res.send('고객 정보 수정'); }) .delete((req, res) => { // HTTP 메소드 GET 요청에 대한 삭제 처리 res.send('고객 정보 삭제'); });

express.Router

라우트 처리를 여러 개의 파일로 분리해 구현이 가능하다.

routes/customer.js

const express = require("express"); const router = express.Router(); router .get("/", (req, res) => { // HTTP 메소드 GET 요청에 대한 조회 처리 res.send("고객 정보 조회"); }) .post("/insert", (req, res) => { // HTTP 메소드 GET 요청에 대한 저장 처리 res.send("신규 고객 추가"); }) .put("/update", (req, res) => { // HTTP 메소드 GET 요청에 대한 수정 처리 res.send("고객 정보 수정"); }) .delete("/delete", (req, res) => { // HTTP 메소드 GET 요청에 대한 삭제 처리 res.send("고객 정보 삭제"); });

routes/product.js

const express = require("express"); const router = express.Router(); router .get("/", (req, res) => { // HTTP 메소드 GET 요청에 대한 조회 처리 res.send("상품 정보 조회"); }) .post("/insert", (req, res) => { // HTTP 메소드 GET 요청에 대한 저장 처리 res.send("신규 상품 추가"); }) .put("/update", (req, res) => { // HTTP 메소드 GET 요청에 대한 수정 처리 res.send("상품 정보 수정"); }) .delete("/delete", (req, res) => { // HTTP 메소드 GET 요청에 대한 삭제 처리 res.send("상품 정보 삭제"); });

app.js

const express = require('express'); const customerRoute = require('./routes/customer'); // customer 라우트를 추가 const productRoute = require('./routes/product'); // product 라우트를 추가 const app = express(); app.use(express.json({ limit: '50mb' // 최대 50메가 })); // 클라이언트 요청 body를 json으로 파싱 처리 app.listen(3000, () => { // 3000번 포트로 웹 서버 실행 console.log('Server started. port 3000.'); }) app.use('/customer', customerRoute); // customer 라우트를 추가하고 기본 경로로 /customer 사용 app.use('/product', productRoute); // product 라우트를 추가하고 기본 경로로 /product 사용

위의 라우터 처리 방식이 이해가 된다면 페이지를 닫지 말고, 코드를 작성하면서 페이지를 만들어보자. 눈으로 백날 보는 거보다 한번 코딩이 더 머릿속에 남기 때문이다.

위의 라우터 처리 방식으로 뒤에서 적용하는 json-server를 이용하면 간단한 CRUD 기능을 만들 수 있다. 다음 글에서는 Express 에러 처리와 정적 파일 제공하는 방법에 대해서 알아보자.

함께 보면 좋은 글

해당 콘텐츠는 프리미엄 구독자 공개(유료) 콘텐츠로 무단 캡쳐 및 불법 공유시 법적 제재를 받을 수 있습니다.

본 콘텐츠는 무료로 제공중입니다.
콘텐츠가 마음에 드셨나요?

펀코딩 구독으로 더 많은 콘텐츠를 만나보세요!