π¦ λ΄μΌλ°°μμΊ ν/TIL(Today I Learned) TIL_220630_rest_framework_simplejwt - restframework-simplejwt μΈμ¦μ μ’ λ₯ 1. μΈμ μΈμ¦ λ°©μ λΈλΌμ°μ μμ μ¬μ©μκ° μΈμ¦(Authentication)μ μννλ©΄ μλ²μμ μ¬μ©μμ μ 보λ₯Ό μ μ₯.μλ΅μΌλ‘ μΈμ (JSESSIONID) ν€λ₯Ό μ΄μ©ν΄ ν΄λΌμ΄μΈνΈ λΈλΌμ°μ μ μΏ ν€μ μΈμ (JSESSIONID)μ μ 보λ₯Ό μ μ₯νκ² λ¨.ν΄λΌμ΄μΈνΈλ λΈλΌμ°μ μΏ ν€μ μ μ₯λ μΈμ μΌλ‘ μ μ₯λ μΈμ μ 보λ₯Ό μ΄μ©ν΄ μΈκ°(Authrization)λ μ 보μ μ κ·Ό νμ©. 2. ν ν° μΈμ¦ λ°©μ ν ν° μΈμ¦ λ°©μμ μ¬μ©μκ° μΈμ¦μ μννλ©΄ μλ²μμλ ν ν°μ μμ±ν λ€μ μ μ₯νμ§ μκ³ (stateless) ν ν°κ°μ μ¬μ©μμ λΈλΌμ°μ μκ² μλ΅ν¨.ν ν°κ°μ μ¬μ©μκ° μΈκ°λ μ¬μ©μλ§ μ¬μ©ν μ μλ μλΉμ€λ₯Ό μμ²ν λ ν¨κ» 보λ΄κ² λκ³ , μλ²μμ μ΄ ν ν°μ μλ―Έ μλ κ°μΌλ‘ ν΄μ λ° μΈμ¦νκ² λ¨.ν ν°μ username, user_id λ± μ¬μ©μλ₯Ό μ€λͺ ν μ μλ λ°μ΄ν°λ₯Ό ν¬ν¨νκ² λ¨.μ°Έκ³ : μ¬μ©μλ₯Ό μ€λͺ ν μ μλ λ°μ΄ν°λ₯Ό ν΄λ μ(claim) μ΄λΌκ³ ν¨. 3. JWT(Json Web Token) ν ν° μΈμ¦ λ°©μμ λνμ£Όμ.JWT ν ν° κ΅¬μ‘°λ {HEADER}.{PAYLOAD}.{VERIFY_SIGNATURE} λ‘ μ΄λ£¨μ΄μ Έ μμ.JWT μμ : {eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9}.{eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ}.{SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c}- μμ κ°μ΄ κ° λ°μ΄ν°λ μ¨μ μΌλ‘ ꡬλΆ. 4. HEADER HEADER λ JWT λ₯Ό κ²μ¦νλλ° νμν μ 보λ₯Ό κ°μ§ λ°μ΄ν°VERIFY_SIGNATURE μ μ¬μ©ν μνΈν μκ³ λ¦¬μ¦κ³Ό ν ν° νμ , key μ id λ±μ μ 보λ₯Ό κ°μ§κ³ μμ.μνΈνλ κ°μ μλ.HEADER μ 보{ "typ": "JWT", # ν ν° νμ "alg": "HS256" # μκ³ λ¦¬μ¦} 5. PAYLOAD μ€μ§μ μΌλ‘ μΈμ¦μ νμν λ°μ΄ν°λ₯Ό μ μ₯.λ°μ΄ν° κ°κ°μ νλλ₯Ό ν΄λ μ(claim)μ΄λΌκ³ νλ€.λλΆλΆμ κ²½μ° ν΄λ μμ username λλ user_id λ₯Ό ν¬ν¨.μΈμ¦μμ payload μ μλ username μ κ°μ Έμμ μ¬μ©μμ μ 보λ₯Ό μΈμ¦ν λ μ¬μ©ν΄μΌ νκΈ° λλ¬Έ.λν payload μμ μ€μνκ² μ΄ν΄λ³΄μμΌ ν μ 보λ ν ν° λ°νμκ°(iat)κ³Ό ν ν° λ§λ£μκ°(exp).ν ν°μ λ§λ£ μκ°μ΄ μ§λλ©΄ μλ‘μ΄ ν ν°μ λ°κΈ λ°μμΌ ν¨. (보μ μ€μ)PAYLOAD μ 보{ "token_type": "access", # ν ν°μ μ’ λ₯. μ¬κΈ°μλ access ν ν°μ λλ€. "exp": 1656293275, # ν ν°μ λ§λ£μκ°μ λλ€. (Numeric Date) "iat": 1656293095, # ν ν°μ λ°νμκ°μ λλ€. (Numeric Date) "jti": "2b45ec59cb1e4da591f9f647cbb9f6a3", # json token id μ λλ€. "user_id": 1 # μ€μ μ¬μ©μμ idκ°μ΄ λ€μ΄μμ΅λλ€.} 6. VERIFY SIGNATURE header μ payload λ μνΈν λμ§ μκ³ λ¨μν Json β UTF-8 β Base64 νμμΌλ‘ λ³νλ λ°μ΄ν°.μ¦ header μ payload μ μμ± μ체λ λ무 μ½κ³ λꡬλ λ§λ€ μ μλ λ°μ΄ν°.λ°λΌμ μ λκ°μ λ°μ΄ν°λ§ μλ€λ©΄ ν ν°μ λν μ§μμ¬λΆ νλ¨μ μ΄λ£¨μ΄μ§ μ μκ² λ¨.κ·Έλμ JWT μ ꡬ쑰μμ κ°μ₯ λ§μ§λ§μ μλ VERIFY SIGNATURE λ ν ν° μ체μ μ§μμ¬λΆλ₯Ό νλ¨νλ μ©λλ‘ μ¬μ©ν¨.VERIFY SIGNATURE λ Base64UrlEncoding λ header μ payload μ μ 보λ₯Ό ν©μΉ λ€ SECRET_KET λ₯Ό μ΄μ©νμ¬ Hash λ₯Ό μμ±νμ¬ μνΈν ν¨.HMACSHA256 ( base64UrlEncode(header) + "." + base64UrlEncode(payload), SECRET_KEY) restframework-simplejwt μ¬μ©λ² νλ‘μ νΈ settings.py 'rest_framework_simplejwt.authentication.JWTAuuthentication' μΆκ° REST_FRAMEWORK = { 'DEFAULT_AUTHENTICATION_CLASSES': [ # session νΉμ tokenμ μΈμ¦ ν ν΄λμ€ μ€μ 'rest_framework_simplejwt.authentication.JWTAuthentication', ],} user μ± urls.py from / import μΆκ° from rest_framework_simplejwt.views import ( TokenObtainPairView, TokenRefreshView,) urlpatterns μΆκ° urlpatterns = [ path('api/token/', TokenObtainPairView.as_view(), name='token_obtain_pair'), path('api/token/refresh/', TokenRefreshView.as_view(), name='token_refresh'),] νλ‘μ νΈ settings.py INSTALLED_APPS μ 'rest_framework_simplejwt' μΆκ° INSTALLED_APPS = [ 'rest_framework_simplejwt',] postman μΌλ‘ ν μ€νΈ user/api/token/ μΌλ‘ username κ³Ό password λ₯Ό λ΄μμ 보λ΄μ£ΌμΈμ. access ν ν°κ³Ό refresh ν ν° νμΈ postman ν μ€νΈ 곡μ νκΈ° URL 볡μ¬μΉ΄μΉ΄μ€ν‘ 곡μ νμ΄μ€λΆ 곡μ μμ€ κ³΅μ κ²μκΈ κ΄λ¦¬ ꡬλ νκΈ°MOVEMENT.DEV Contents restframework-simplejwt μΈμ¦μμ’ λ₯ 1.μΈμ μΈμ¦λ°©μ restframework-simplejwt μ¬μ©λ² λΉμ μ΄ μ’μν λ§ν μ½ν μΈ TIL_220703_ν νλ‘μ νΈ 2023.01.01 TIL_220627_μ ν μ μ νλ‘μ νΈ SA 2023.01.01 TIL_220623_λ₯λ¬λ 2023.01.01 TIL_220621_DRF κ°μ 2023.01.01 λκΈ 0 + μ΄μ λκΈ λ보기