JWT는 JSON Web Token의 약자로 JSON 파일의 변조를 체크하기 위해 고안되었습니다. 비밀키를 이용한 해쉬 알고리즘을 통해 암호화하게 되며 이를 복호화하는 과정에서 토큰의 변조 여부를 알 수 있습니다.
JWT 토큰은 세 부분으로 구성되어 있습니다.
Heaer: 암호화 방식 대한 정보
Payload: JSON 포맷에 해당되는 내용
Signature: 무결성을 보장하는 부분으로 Header, Payload를 비밀키를 통해 암호화한 값
Heaer와 Payload는 알려진 디코딩 방식으로 해독이 가능하며 변조도 가능합니다. 그렇기에 중요한 정보는 담지 않아야 합니다!!
Payload를 변조하더라도 Signature의 부분에서 암호화된 것과 다르기에 변조 여부를 쉽게 알 수 있게 됩니다.
(https://jwt.io/ 에서 JWT 토큰으로 Payload의 내용을 확인할 수 있음.)
쿠키, 세션을 이용한 로그인 기능과 다음의 차이가 있습니다.
@app.route('/createToken', methods=['POST'])
def createToken():
payload = {
'Hello': 'Test!!!!',
'World': 'Hi!!',
'exp': datetime.utcnow() + timedelta(seconds=5) # 토큰 5초 유지
}
token = jwt.encode(payload, SECRET_KEY, algorithm='HS256').decode('utf8') # 토큰 발급
return jsonify({'result': '생성 완료', 'token': token})
token_receive = request.cookies.get('mytoken')
if token_receive is None: # 토큰 없음
return render_template('index.html', msg="토큰 없음")
try:
payload = jwt.decode(token_receive, SECRET_KEY, algorithms=['HS256'])
print("클라이언트에서 복호화한 페이로드: ", payload)
return render_template('index.html', msg="정상적인 토큰") # 토큰 정상
except jwt.ExpiredSignatureError: # 타임 아웃
return render_template('index.html', msg="시간 초과")
except jwt.exceptions.DecodeError: # 토큰 비정상
return render_template('index.html', msg="잘못된 토큰")