[Jest] beforeEach, afterEach

마데슾 : My Dev Space·2020년 3월 24일
0

Test Code

목록 보기
1/1

promise sprint를 하던중 이슈가 생겼다.

const fs = require("fs");
const util = require("util");

const {
  getBodyFromGetRequestPromise,
  getDataFromFilePromise
} = require("../exercises/02_promiseConstructor");

const writeFilePromise = util.promisify(fs.writeFile);

const BASE_URL = "https://koreanjson.com/users/";

const fetchUsersAndWriteToFileAsync = async (readFilePath, writeFilePath) => {
  const dataList = await getDataFromFilePromise(readFilePath);

  const responseDataList = await Promise.all(
    dataList.map(id => getBodyFromGetRequestPromise(BASE_URL + id))
  );

  const text = responseDataList.map(data => data.name).join("\n") + "\n";

  writeFilePromise(writeFilePath, text); // < 이슈 부분 >
};

테스트케이스,

const fs = require("fs");

const { fetchUsersAndWriteToFileAsync } = require("../exercises/05_asyncAwait");

describe("Async & Await Test", () => {
  describe("fetchUsersAndWriteToFileAsync", () => {
    const readFilePath = "files/read/userId.txt";
    const writeFilePath = "files/write/userName.txt";

    beforeEach(() => {
      fs.writeFileSync(writeFilePath, "");
    });

    // afterEach 라는 hook을 보면, ""으로 내용을 비우는 코드가 작성되어 있습니다.
    afterEach(() => {
      fs.writeFileSync(writeFilePath, "");
    });

    test("should return the promise created by the entire chain", () => {
      const result = fetchUsersAndWriteToFileAsync(readFilePath, writeFilePath);
      expect(result.constructor.name).toBe("Promise");
    });

    test("should eventually write a user name to a file", () => {
      return fetchUsersAndWriteToFileAsync(readFilePath, writeFilePath).then(
        () => {
          const userNames = fs.readFileSync(writeFilePath, "utf8");
          expect(userNames).toBe("이정도\n김재완\n김성은\n이주연\n구일모\n");
        }
      );
    });
  });
});

이슈

case1 ) writeFilePromise(writeFilePath, text)

  • test : 테스트 통과 X
  • userName.txt : 파일에 내용이 남아있음

case1 ) await writeFilePromise(writeFilePath, text)

  • test : 테스트 통과 O
  • userName.txt : 파일에 내용이 남아있지않음

궁금한부분 ) 왜 await를 붙여야 테스트가 통과하고 userName.txt에 내용이 남지 않을까?

테스트를 잘 보면 그 이유를 알 수 있다..!!

beforeEach, afterEach는 jest에서 제공하는 도우미 기능이다.

beforeEach는 테스트가 실행되기 전에 초기화 시켜주는 기능을 한다.

beforeEach(() => {
  fs.writeFileSync(writeFilePath, "");
});

afterEach는 테스트가 종료되고 상황을 정리해주는 기능을 한다. ( 테스트가 성공하지 않으면 실행되지 않는다 )

afterEach(() => {
  fs.writeFileSync(writeFilePath, "");
});

위의 내용을 참고하여 아래의 코드를 보면,

return fetchUsersAndWriteToFileAsync(readFilePath, writeFilePath).then(
  () => {
    const userNames = fs.readFileSync(writeFilePath, "utf8");
    expect(userNames).toBe("이정도\n김재완\n김성은\n이주연\n구일모\n");
  }
);

테스트에서 fetchUsersAndWriteToFileAsync(readFilePath, writeFilePath)를 실행시킨후 then으로 파일내용을 읽어와 비교하고 있기때문에 fetchUsersAndWriteToFileAsync 함수에서 await없이 writeFilePromise(writeFilePath, text)를 실행해주면 비동기함수이기 때문에 함수가 실행이 끝날때까지 기다려주지 않아서 ''과 비교하게 되고 await를 사용해주면 함수 실행이 끝날때까지 기다려주기 때문에 파일을 다 읽어온후 비교해줘서 테스트가 정상적으로 통과되고 테스트가 통과되었으니 afterEach가 실행되어 userName.txt"" 빈문자열로 저장되는 것이다.

profile
👩🏻‍💻 🚀

0개의 댓글