단위 테스트 (Unit Test): 가장 작은 규모의 기능을 테스트합니다.
통합 테스트 (Integration Test): 다양한 기능을 합쳤을때 생기는 문제를 방지하기 위한 테스트입니다.
E2E 테스트 (End-to-end Test): 끝에서 끝(종단 간)을 의미하는 End to end 테스트입니다.
쉽게 말하면 백엔드부터 시작해서 최종적으로 웹 페이지가 원하는대로 동작하며 원하는 데이터를 잘 보여주는지 확인합니다.
이외에도 개발자들은 돌연변이 테스트와 같은 다양한 기법들로 자신들의 서비스가 더욱 치밀하고 탄탄한 서비스로 거듭날 수 있도록 노력하고 있습니다 🙂
💡 번외) 넷플릭스는 자신들의 서버가 아무때나 무작위로 다운되도록 해서 자신들의 인프라에 약점이 있는지 찾아내는것을 도와주는 ["카오스 몽키"라는 솔루션](https://www.itworld.co.kr/news/152680)을 개발해서 사용했습니다. (카오스 엔지니어링)언제든 서버가 죽더라도 최대한 빠르게 자동으로 서버를 재구성하는 환경으로 운영할 수 있습니다.
Jest를 사용해보도록 하겠습니다!Jest는 출시한지 얼마 지나지 않아 주목받았는데요, 페이스북에서 개발한 프론트엔드 라이브러리인 React.js와도 궁합이 아주 좋기 때문에 엄청난 성장세를 보이며 2022년 기준 JavaScript 개발자들 사이에서 가장 많이 사용되는 테스팅 프레임워크로 뽑혔습니다. → Nest.js 프레임워크에서도 기본 지원하는 테스팅 프레임워크랍니다. 😉
[테스팅 프레임워크 사용률 지표] 파란색이 Jest, 그 외엔 원래 존재하던 테스팅 프레임워크Jest는 다른 테스팅 프레임워크와 비교하면 여러가지 장점이 있지만, 그 중 가장 제일이라고 생각되는것은 테스트 코드의 표현이 다른 프레임워크보다 훨씬 간결합니다. 그렇기 때문에 여전히 많은 자바스크립트 개발자들에게 사랑받고 있습니다 😉Jest를 간단하게 사용해보기 위해 새로운 프로젝트를 구성해보겠습니다! 프로젝트로 사용할 폴더를 만들고, 그 폴더를 VS Code로 열어주세요! 그리고 언제나처럼 yarn을 이용하여 모듈을 설치합니다! (공식 문서 참고)# yarn 프로젝트를 초기화합니다.
yarn init -y
# DevDependencies로 jest를 설치합니다.
yarn add -D jest{
...
"main": "index.js",
"license": "MIT",
...
} "license": "MIT", 다음 줄에서, 아래의 내용을 복사해주세요!{
...
"type": "module",
"scripts": {
"test": "node --experimental-vm-modules node_modules/.bin/jest"
},
...
} 이렇게 하면, jest를 yarn test 와 같은 명령어로 실행시킬 수 있습니다. 또한 이렇게 하는것이 모범 사례로 꼽힙니다 😉validation.js 라는 이름으로 파일을 하나 생성해주세요! 그리고 아래의 코드 스니펫을 복사해 validation.js 파일에 붙여넣고 저장해주세요!// validation.js
export const isEmail = (value) => {
// value가 이메일 형식에 맞으면 true, 형식에 맞지 않으면 false를 return 하도록 구현해보세요
return false;
};test(): 단위 테스트를 묶어주는 함수입니다.
expect(): 특정 값이 만족되는지(정상적인지) 확인하기 위한 표현식을 작성할수 있게 해주는 함수입니다.
이 설명만 보면 잘 모르겠죠? 아래 예시를 참고해주세요!
[코드스니펫] 테스트코드 예시
```jsx
// validation.spec.js
import { isEmail } from './validation';
test('테스트가 성공하는 상황', () => {
expect(isEmail('이메일이 아니에요')).toEqual(false);
});
test('테스트가 실패하는 상황', () => {
expect(isEmail('my-email@domain.com')).toEqual(true);
});
```
위 예시를 validation.spec.js 에 붙여넣어 저장한 뒤, yarn test 명령어를 실행했을때 아래와 같이 뜨면 정상적인 상황입니다!

yarn test 명령어를 이용해 테스트 코드를 실행해보세요!
위 사진처럼 failed가 있도록. 즉, 실패하는 테스트가 최소 하나라도 있도록 작성해주세요!! 저희가 항상 false를 return 하도록 구현해둔 함수 때문이긴 하지만 저희는 지금부터 테스트 코드를 통해 여러분의 코드에 결함이 있다는것을 스스로 증명할 수 있게 되었어요! 🎉 개발자는 항상 모든걸 확인하고 증명하는 역할임을 잊지 마세요!
💪 만약 항상 모든 코드가 성공한다면 지금 작성한 테스트 코드에 **빈틈이 많으며**, 자신의 코드의 **결함을 찾지 못하는 테스트 코드**를 작성하신거랍니다! 🥲
isEmail 함수 코드 디버깅export const isEmail = (value) => {
const email = (value || '');
if (email.split('@').length !== 2) {
return false;
} else if (email.includes(' ')) {
return false;
} else if (email[0] === '-') {
return false;
}
return true;
};
추가된 요구사항은 아래와 같습니다.
여러분은 다행히 테스트 코드를 작성해두었기 때문에 지금 구현해둔 함수가 위 요구사항에 맞게 동작하는지 쉽게 확인할 수 있어요!!
그러면, 위 요구사항을 만족시키도록 테스트 코드를 추가로 작성해주세요!
...
test("입력한 이메일 주소중, 로컬 파트(골뱅이 기준 앞부분)에는 영문 대소문자와 숫자, 특수문자는 덧셈기호(+), 하이픈(-), 언더바(_) 3개 외에 다른 값이 존재하면 이메일 형식이 아니다.", () => {
expect(isEmail('_good-Email+test99@domain.com')).toEqual(true);
expect(isEmail('my$bad-Email9999@domain.com')).toEqual(false);
});
test("입력한 이메일 주소중, 도메인(골뱅이 기준 뒷부분)에는 영문 대소문자와 숫자, 하이픈(-) 외에 다른 값이 존재하면 이메일 형식이 아니다.", () => {
expect(isEmail('my-email@my-Domain99.com')).toEqual(true);
expect(isEmail('my-email@my_Domain99.com')).toEqual(false);
expect(isEmail('my-email@my$Domain99.com')).toEqual(false);
});
2) isEmail 함수 다시 디버깅
추가 요구사항에 대한 isEmail 함수 디버깅 예시
// validation.js
export const isEmail = (value) => {
const email = value || "";
const [localPart, domain, ...etc] = email.split("@");
if (!localPart || !domain || etc.length) {
return false;
} else if (email.includes(" ")) {
return false;
} else if (email[0] === "-") {
return false;
}
for (const word of localPart.toLowerCase().split("")) {
if (!["a","b","c","d","e","f","g","h","i","j","k","l","m","n","o","p","q","r","s","t","u","v","w","x","y","z","0","1","2","3","4","5","6","7","8","9","-","+","_"].includes(word)) {
return false;
}
}
for (const word of domain.toLowerCase().split("")) {
if (!["a","b","c","d","e","f","g","h","i","j","k","l","m","n","o","p","q","r","s","t","u","v","w","x","y","z","0","1","2","3","4","5","6","7","8","9","-", "."].includes(word)) {
return false;
}
}
return true;
};
정규 표현식을 이용한 isEmail 함수는 어떻게 만들까요?
// validation.js
export const isEmail = (value) => {
const email = value || "";
const [localPart, domain, ...etc] = email.split("@");
if (!localPart || !domain || etc.length) {
return false;
} else if (email.includes(" ")) {
return false;
} else if (email[0] === "-") {
return false;
} else if (!/^[a-z0-9+_-]+/gi.test(domain)) {
return false;
}
return true;
};