일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
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 | 29 | 30 | 31 |
- 코플릿
- 재귀함수
- 프로그래머스
- array.slice()
- 코딩공부
- join
- Programmers
- Where
- MySQL
- array.push()
- for문
- 최강의 인생
- Developer_JoyKim
- 코딩테스트
- array
- 코드스테이츠
- Algorithms
- 알고리즘
- 배열
- select
- 역행자
- 정규표현식
- Hackerrank
- 개발자_조이킴
- SQL
- node.js
- 블록체인
- JavaScript
- 자바스크립트
- 개발자의 책장
- Today
- Total
CodingSpace
[NodeJS/Express] express-validator 라이브러리를 이용한 유효성 검사 구현 본문
Intro.
유효성 검사(validation)는 말 그대로 유저(클라이언트)로부터 서버로
전달된 데이터가 유효한지를 검사하는 것을 의미합니다.
express를 사용하는 경우,
유효성 검사 기능을 구현하기 위해
주로 class-validator와 express-validator 라이브러리를 사용합니다.
이번 글에서는 express-validator 라이브러리를 사용해
유효성 검사를 구현해봅니다.
Description.
1. npm 프로젝트 시작하기
npm init 명령어를 입력해서 새로운 프로젝트를 생성한다!
// npm 프로젝트 생성
npm init
명령어를 입력하고 Enter를 계속 입력해주면
package.json 파일이 생성된다!
2. express, express-validator 설치하기
npm install express express-validator 명령어를 입력해서 express와 express-validator를 설치한다.
// express, express-validator 설치
npm install express express-validator
3. POST 요청에서 body 값 유효성 검사 구현
먼저 POST 요청에서 전달되는 body 값 유효성 검사를 구현해보자.
유효성 검사는 Router 레벨에 적용했다.
테스트가 진행될 POST 요청 예제는 '회원가입(signup)'으로 선택했다.
body 값의 각 파라미터 유효성 조건은 다음과 같이 정했다:
- email
- required 파라미터
- 이메일 형식 (ex. joykim9311@gmail.com)
- password
- required 파라미터
- 최소 길이: 4
- 최대 길이: 25
- 영어 대소문자 포함
3.1. express-validator 함수
email과 password 파라미터 유효성 검사를 위해 express-validator 내장 함수들을 사용했다:
- notEmpty()
- isEmail()
- isLength()
- matches
유효성 검사를 통과하지 못했을 때
각 유효성 검사에 매칭되는 에러 메시지를 표현하기 위해
withMessage() 내장 함수를 사용했다.
- withMessage()
3.2. Router 레벨에 적용한 유효성 검사 코드
앞서 이야기한대로 유효성 검사는 Router 레벨에서 이뤄지도록 구현했다.
// user.route.js 파일
import express from "express";
import { check, } from "express-validator";
import UserController from "../controller/user.controller.js";
const userController = new UserController();
const userRoute = express.Router();
userRoute.post(
'/signup', [
check('email') // email 파라미터 유효성 검사
.notEmpty() // 1. 파라미터가 비어있으면 에러
.withMessage(`email parameter is empty`)
.isEmail() // 2. 파라미터가 이메일 형식이 아니면 에러
.withMessage(`email parameter is not email format`)
,
check('password') // password 파라미터 유효성 검사
.notEmpty() // 1. 파라미터가 비어있으면 에러
.withMessage(`password parameter is empty`)
.isLength({ // 2. 파라미터의 길이가 4이상 25이하가 아니면 에러
min: 4,
max: 25
})
.withMessage(`password parameter is satisfied by following a condition; 4 <= password.length <= 25`)
.matches(/^.*[a-z].*$/)
.withMessage(`password parameter should contain at least one lower case`)
.matches(/^.*[A-Z].*$/)
.withMessage(`password parameter should contain at least one upper case`)
],
userController.signup
);
export default userRoute;
3.3. 유효성 검사 에러 확인 및 반환
유효성 검사를 통과하지 못하면 에러가 생성된다.
생성된 에러들은 express-validator 내장 함수 validationResult()를 사용해 받을 수 있다.
코드의 가독성을 높이고자
유효성 검사를 통해 생성된 에러 확인 및 반환은
Controller에서 구현했다. (에러 확인 및 반환을 middleware로 따로 구현하면 코드 가독성을 더 향상시킬 수 있음!)
// user.controller.js
import UserService from "../service/user.service.js";
import { validationResult } from "express-validator";
export default class UserController {
constructor() {
this.userService = new UserService();
}
signup = (req, res) => {
// 유효성 검사에서 생성된 에러를 errors 변수로 받는다
const errors = validationResult(req);
// 유효성 검사에서 생성된 에러가 있는 경우
// 400 상태코드와 함께 에러들을 반환한다.
if (!errors.isEmpty()) {
return res.status(400).send(errors.array());
}
// 유효성 검사를 통과한 경우
// 유저를 DB에 추가한다 (본 프로젝트에서는 DB가 아닌 서버 메모리에서 처리함)
const { email, password } = req.body;
const userInfo = {
email,
password,
}
const user = this.userService.createUser(userInfo);
res.status(201).send({
success: true,
message: `user is created`,
data: user,
});
}
}
3.4. Postman 유효성 검사 테스트
설계한대로 유효성 검사 기능이 구현되었는지 확인하고자 Postman을 사용하여 테스트를 진행했다.
1) email 파라미터가 비어있는 경우
notEmpty() 및 isEmail() 함수 모두 통과하지 못해 2가지 에러가 발생했다.
2) password 파라미터의 길이가 4보다 작거나 25보다 큰 경우
isLength() 함수를 통과하지 못해 에러가 발생했다.
3) password 파라미터에 영어 대소문자가 포함되지 않은 경우
matches() 함수를 통과하지 못해 에러가 발생했다.
4) 모든 유효성 검사가 통과되고 유저가 생성된 경우
References.
- 전체 코드:
1) 프로젝트 구조
2) app.js
// app.js
import express from "express";
import userRoute from "./routes/user.route.js";
const app = express();
const port = 3333;
app.use(express.json());
app.use('/user', userRoute);
app.get('/', (req, res) => {
console.log('server for express-validator example');
});
app.listen(port, () => {
console.log(`server is running at ${port}`);
});
3) user.route.js
// user.route.js
import express from "express";
import { check, } from "express-validator";
import UserController from "../controller/user.controller.js";
const userController = new UserController();
const userRoute = express.Router();
userRoute.post(
'/signup', [
check('email')
.notEmpty()
.withMessage(`email parameter is empty`)
.isEmail()
.withMessage(`email parameter is not email format`)
,
check('password')
.notEmpty()
.withMessage(`password parameter is empty`)
.isLength({
min: 4,
max: 25
})
.withMessage(`password parameter is satisfied by following a condition; 4 <= password.length <= 25`)
.matches(/^.*[a-z].*$/)
.withMessage(`password parameter should contain at least one lower case`)
.matches(/^.*[A-Z].*$/)
.withMessage(`password parameter should contain at least one upper case`)
],
userController.signup
);
userRoute.get(
'/:userNo', [
check('userNo')
.isInt()
],
userController.selectUser
);
export default userRoute;
4) user.controller.js
// user.controller.js
import UserService from "../service/user.service.js";
import { validationResult } from "express-validator";
export default class UserController {
constructor() {
this.userService = new UserService();
}
signup = (req, res) => {
const errors = validationResult(req);
if (!errors.isEmpty()) {
return res.status(400).send(errors.array());
}
const { email, password } = req.body;
const userInfo = {
email,
password,
}
const user = this.userService.createUser(userInfo);
res.status(201).send({
success: true,
message: `user is created`,
data: user,
});
}
selectUser = (req, res) => {
const errors = validationResult(req);
if (!errors.isEmpty()) {
return res.status(400).send(errors.array());
}
const userNo = req.params.userNo
const user = this.userService.selectUser(userNo);
res.status(200).send({
success: true,
message: `user is selected`,
data: user,
});
}
}
5) user.service.js
// user.service.js
export default class UserService {
constructor() {
// 생성된 유저들을 담는 배열
this.userList = [];
// 유저의 번호 (unique)
this.userNo = 0;
}
createUser = (userInfo) => {
userInfo['no'] = this.userNo;
this.userNo = this.userNo + 1;
this.userList.push(userInfo);
return userInfo;
}
selectUser = (userNo) => {
return this.userList[userNo];
}
}
- express-validator 공식 문서: https://express-validator.github.io/docs/index.html
- node.js + express 이미지 출처: https://velog.io/@gidong_e/Node.js-Express
'Back-End > NodeJS' 카테고리의 다른 글
[Jest] 에러 해결 - ReferenceError: You are trying to `import` a file after the Jest environment has been torn down (2) | 2023.05.28 |
---|---|
[NodeJS/Express] passport 미들웨어로 Google OAuth 2.0 구현하기 (1) (0) | 2022.12.23 |
[NodeJS/Express] req.body에 undefined가 발생했을 때 (0) | 2022.12.22 |
[NodeJS/Express] 미들웨어로 에러 처리 (0) | 2022.12.21 |