JEST jwt 테스팅

unn04012·2021년 8월 6일

Jest

모킹

  • 테스팅을 할 때 실제 모듈을 사용할 수 없을 때 이용한다.
  • 만약 jsonwebtoken 모듈을 이용할 경우 실제로 검증을 할 수 없기 때문에 이럴 때 사용한다.
jest.mock('jsonwebtoken');
import jwt from 'jsonwebtoken';
  • 아래코드는 테스팅 하기 위한 미들웨어 함수이다.
const verifyToken = (req, res, next) => {
  try{        
    req.decoded = jwt.verify(req.headers.authorization, process.env.JWT_SECRET);        
    return next();
  }catch(error){  
    console.log(error)  ;
    if(error.name === 'TokenExpiredError'){
      return res.status(419).json({
        code : 419,
        message : '토큰이 만료되었습니다.',
      });
    }
    return res.status(401).json({
      code: 401,
      message : '유효하지 않은 토큰입니다',
    })
  }    
}
  • 테스트를 진행하기 위해 실제 토큰을 생성한다.
// middlewares.test.js
const res = {
        status : jest.fn(() => res),
        json : jest.fn(),
};
const next = jest.fn();
test('success for jwt.verfiy method', () => {
        const token = jwt.sign({
            id : '1',
            nick : 'mun',
        }, process.env.JWT_SECRET, {
            expiresIn : '1m',
            issuer: 'unn04012',
        });
        const req = {
            headers : {
                authorization : token
            }
        };
        verifyToken(req, res, next);
        expect(next).toBeCalledTimes(1);
    });
  • req, res, next 변수를 가짜 객체를 만들어 해당 테스트만 동작하게 만든다.
  • req 객체에는 많은 속성들이 있지만 위 테스트 코드가 동작하기 위해서는 headers.authorization 속성만 존재하면 된다.
  • 후에 verifyToken(req,res,next) 미들웨어를 실행 한 후 next() 함수가 실행이 됬는지 확인한다.
test('expired for jwt.verify method', () => {
        const req = {
            headers : {
                authorization : expiredToken,
            }
        };                        
        const error = {name : 'TokenExpiredError'};
        **jwt.verify.mockImplementation(() => {
            throw error;
        });**
        verifyToken(req, res, next);        
        expect(res.status).toBeCalledWith(419);        
        expect(res.json).toBeCalledWith({
            code : 419,
            message : '토큰이 만료되었습니다.',            
        })        
    });
  • 위 코드는 토큰은 유효하지만 만료되었을 때 실행되는 테스트코드이다.
  • 실제 실행코드 부분에서 try ..catch 구문에서 catch 부분, 즉 에러를 일으켜야 하기 떄문에 mockImplementation()함수로 error를 실행시키고 이름은 TokenExpiredError로 선언하였다.
  • 만약 jwt.verify() 메서드가 Promise 객체였다면 Promise.reject(error) 구문으로 실행을 시켰다.
  • 후에 res.json() 함수에서 해당 객체가 확인한다.
test('invalid jwt token', () => {                
        const req = {
            headers : {
                authorization : expiredToken,
            }
        };                        
        const error = {name : 'TokenInvalid'};
        jwt.verify.mockImplementation(() => {
            throw error;
        });
        verifyToken(req, res, next);        
        expect(res.status).toBeCalledWith(401);        
        expect(res.json).toBeCalledWith({            
                code : 401,
                message : '유효하지 않은 토큰입니다',            
        })
    })
  • 마지막 부분은 유효하지 않은 에러를 일으키는 테스팅 코드이다.
  • 이번에는 error 속성에 아무 이름이나 넣어서 테스트를 진행했다.
profile
백엔드 개발자

0개의 댓글