JWT 토큰 인증방식에대해 알아보자.

hipAn·2022년 9월 25일
0

끄적끄적 성장일지

목록 보기
2/30

이번 1주차 미니프로젝트에서 내가 맡은 파트가 로그인&회원가입&로그아웃 기능과 팀원들이 각자 만든 html페이지를
-(우리는 깃허브를 할 줄 아는사람도 없었고 각자 빠르게 공부를 하고 시작해보자고 하였으나... 개인개인 각자가 모두 한마음은 아니었기에.. 실패하였다...)

내가 받아서 서버를 짜고 api를 연결시켰다.

이 과정에서 JWT를 사용하게되었는데 이를 직접적으로 사용해보면서 막연하기만 했던 JWT라는것에 대해 개념이 조금이나마 잡힌듯하다.

JWT란 존뫗ㅌ의 약ㅈ... 줴이슨 웹 퉈큰 의 약자이다.

간략하게는 JWT는 사용자를 인증하고 식별하기 위한 토큰기반 인증인것이다.

검색해보면 블라 블라 긴 내용들이 많은데 나정도 수준에서 알아듣기 쉽게 풀어보자면

JWT는 클라이언트를 이용하는 이용다가 아이디와 패스워드를 통해 웹서비스에서 인증을하고 (로그인) => 서버에서 서명되어진 존왓퉹토ㅋ.. 제이슨 웹 토큰 JWT를 만들어서 클라이언트로 다시 되돌려주게된다.

이상태에서 인증된 사용자는 예를들어 다른페이지로 이동한다던가 어떠한 정보를 요청한다던가 서버에 무언가를 요청할때 아까 돌려받은 JWT를 첨부해서 서버에 함께 전달하게된다.

그러면 서버는 요청을 먼저 처리하기전에 JWT를 확인하고
"아 ㅇㅋ 내가준놈이네 확인." 이후에 요청을 처리해주는 방식인것이다.

JWT 구조를 살펴보자면

JWT는 . 을 구분자로 나누어지는 세 가지 문자열의 조합이다.

  • .을 기준으로 좌측부터 Header, Payload, Signature를 의미한다.

  • Header 에는 JWT 에서 사용할 타입과 해시 알고리즘의 종류가 담겨있으며,

  • Payload 는 서버에서 첨부한 사용자 권한 정보와 데이터가 담겨있다. 마지막으로

  • Signature 에는 Header, Payload 를 Base64 URL-safe Encode 를 한 이후 Header 에 명시된 해시함수를 적용하고, 개인키(Private Key)로 서명한 전자서명이 담겨있다.

전자서명에는 비대칭 암호화 알고리즘을 사용하므로 암호화를 위한 키와 복호화를 위한 키가 다르다. 암호화(전자서명)에는 개인키를, 복호화(검증)에는 공개키를 사용한다.

실제 디코딩된 JWT는 다음과 같은 구조를 지닌다.

  • Header
    json-web-token
    alg : 서명 암호화 알고리즘(ex: HMAC SHA256, RSA)
    typ : 토큰 유형
  • Payload
    토큰에서 사용할 정보의 조각들인 Claim 이 담겨있다. (실제 JWT 를 통해서 알 수 있는 데이터)

  • 즉, 서버와 클라이언트가 주고받는 시스템에서 실제로 사용될 정보에 대한 내용을 담고 있는 섹션이다.

(근데 "claim" 이 뭐시당가..?? === key-value 형식으로 이루어진 한 쌍의 정보를 Claim이라고 칭한다.)

  • 페이로드는 정해진 데이터 타입은 없지만, 대표적으로 Registered claims, Public claims, Private claims 이렇게 세 가지로 나뉜다.

  • Registed claims : 미리 정의된 클레임.
    iss(issuer; 발행자),
    exp(expireation time; 만료 시간),
    sub(subject; 제목),
    iat(issued At; 발행 시간),
    jti(JWI ID)
    Public claims : 사용자가 정의할 수 있는 클레임 공개용 정보 전달을 위해 사용.
    Private claims : 해당하는 당사자들 간에 정보를 공유하기 위해 만들어진 사용자 지정 클레임. 외부에 공개되도 상관없지만 해당 유저를 특정할 수 있는 정보들을 담는다

  • Signature
    시그니처에서 사용하는 알고리즘은 헤더에서 정의한 알고리즘 방식(alg)을 활용한다.

  • 시그니처의 구조는 (헤더 + 페이로드)와 서버가 갖고 있는 유일한 key 값을 합친 것을 헤더에서 정의한 알고리즘으로 암호화를 한다.

JWT에 대해 찾아보다보면 알게되는것은 결국 페이로드부분은 복호화를 하면 그냥 그 안에 저장되어있는 정보들이 다 드러나서 보이게된다.

실제로 내가 JWT 사이트에서 인코딩과 디코딩을 요래 조래 해보기도하고 내가 만들고있는 토이프로젝트 사이트에 적용시켜서 실제로 중간에서 토큰값을 가로채 복화하고 정보를 빼내보는 것도 시도해보다보니 어쩌다 성공을 하게되었다. (물론 내가 만든 구조여서 굉장히 자유롭게 데이터에 접근할수있어서 가능했겠지만)

그로인해 "그럼 이게 뭔 소용이지? 그냥 그럴싸해보이는 인증방식 아닌가..?" 싶었는데 구글링을 하며 찾아보니 아래와 같이 설명되어있었다.

  • JWT은 서명(인증)이 목적이다.
    JWT는 Base64로 암호화를 하기 때문에 디버거를 사용해서 인코딩된 JWT를 1초만에 복호화할 수 있다.
    복호화 하면 사용자의 데이터를 담은 Payload 부분이 그대로 노출되어 버린다. 그래서 페이로드에는 비밀번호와 같은 민감한 정보는 넣지 말아야 한다.
    토큰의 진짜 목적은 정보 보호가 아닌, 위조 방지이다.
    바로 위에서 소개했듯이, 시그니처에 사용된 비밀키가 노출되지 않는이상 데이터를 위조해도 시그니처 부분에서 바로 걸러지기 때문이다.

그렇다. JWT는 정보 보호가 주된 목적이라기보단 위조 방지에 초점을 두고 있는 구조였던것이다!

그렇다면 이것과 혼용해서 정보보호까지도 같이 할 수 있는 무언가가 있지 않을까? 라고 생각을 하던 찰나 또 찾아보다보니 역시 그런게 존재했었다. (나같은 바보만 모르고 있던거였지)

실제로 현업에서는 엑세스토큰,리프레쉬 토큰 으로 나누어 이중 인증을 하는 방식을 사용한다고 한다.

Access Token과 Refresh Token은 따로 좀 찾아보고 한번 적용해보는 연습을 해야겠다.

0개의 댓글