JSON Web Tokenãšã¯äœã§ããïŒ
ããŒã«ãŒã¯å®éã«ã¯éåžžã«åçŽã§ãã æ¯æ¥ãªãã£ã¹ã«å ¥å®€ããå©ããåããŠãããŒã«ãŒãã«ãŒãã®åœ¢ã®ããŒãšããŠæ³åããŠãã ããã äŒç€Ÿã«éããããšããé転å 蚱蚌ã瀟äŒä¿éçªå·ãªã©ã®è³æ Œæ å ±ã®ã»ãããæäŸããããšã«ããã身å ïŒãã°ã€ã³ïŒã確èªããŸããã ãã®ããŒã¿ãšåŒãæãã«ã建ç©å ã«ããããšãã§ããããŒïŒããŒã«ãŒïŒãäžããããŸããã ä»äºãèŸãããã解éïŒãã°ã¢ãŠãïŒãããå ŽåãäŒç€Ÿã¯åã«ããŒããªãã«ããããšãã§ããŸãã ãã¡ããããã®ããŒã¯ããªãã®ãã±ããã«æ®ã£ãŠãããããããŸããããããã¯ããªãã«è¯ããã®ãäžããŸããã
JSON Web Tokenã¯ãç¹å¥ãªåœ¢åŒã®ã·ã³ãã«ãªããŒã¯ã³ã§ãã ãã©ãŒãããã¯æšæºåãããŠããŸããããå€ãã¯ãã§ã«ãã®å®è£ ïŒ JWT ïŒã®1ã€ã䜿çšããŠããŸãã
JWT ïŒçºé³çºé³ïŒã¯3ã€ã®éšåã§æ§æãããŠããŸãã
- èŠåºã
- ãã€ããŒã
- 眲å
å®è£ ãæãäžããåã«ããããããèŠãŠã¿ãŸãããã
èŠåºã
ããã©ã«ãã§ã¯ãããããŒã«ã¯ãæå·åã«äœ¿çšãããããŒã¯ã³ã®ã¿ã€ããšã¢ã«ãŽãªãºã ã®ã¿ãå«ãŸããŸãã
ããŒã«ãŒã®ã¿ã€ãã¯ãtypãããŒã«ä¿åãããŸãã JWTã§ã¯ãtypãããŒã¯ç¡èŠãããŸãïŒããã¯ãã®èšäºã§ã¯éèŠã§ã¯ãããŸããããçç±ã確èªããããã«èªãããšãã§ããŸã ïŒã typããŒãååšããå Žåããã®ãªããžã§ã¯ããJSON WebããŒã¯ã³ã§ããããšã瀺ãããã«ããã®å€ã¯JWTã§ãªããã°ãªããŸããã
2çªç®ã®algããŒã¯ãããŒã¯ã³ã®æå·åã«äœ¿çšãããã¢ã«ãŽãªãºã ãå®çŸ©ããŸãã ããã©ã«ãã§ã¯ãHS256ã«èšå®ããå¿ èŠããããŸãã ããŸããŸãªå®è£ ã§äœ¿çšãããå€ãã®ä»£æ¿ã¢ã«ãŽãªãºã ããããŸãã ã©ã€ãã©ãªã®å®å šãªãªã¹ãã¯ãJWT.ioã«ãããŸãã
ããããŒã¯base64ã§ãšã³ã³ãŒããããŸãã
ãã€ããŒã
ãã€ããŒãã«ã¯ãæ€èšŒãå¿ èŠãªæ å ±ããã¹ãŠæ ŒçŽãããŸãã ãã€ããŒãã®åããŒã¯ãã¹ããŒãã¡ã³ãããšåŒã°ããŸãã ããšãã°ãæåŸ ã«ãã£ãŠã®ã¿ã³ãã¥ããã£ã«åå ã§ãããœãŒã·ã£ã«ãããã¯ãŒã¯ãèããŠã¿ãŸãããã ã³ãã¥ããã£ã«èª°ããæåŸ ããããšãã¯ãæåŸ ç¶ãéããŸãã é»åã¡ãŒã«ã¢ãã¬ã¹ãæåŸ ãåãå ¥ãã人ã®ãã®ã§ããããšã確èªããããšãéèŠã§ãããã®ããããã®ã¢ãã¬ã¹ããã€ããŒãã«å«ããŸãããã®ããããé»åã¡ãŒã«ãããŒã«ä¿åããŸãã
{ "email": "example@jamesbrewer.io" }
ãã€ããŒãã®ããŒã¯ä»»æã§ãã ãã ããç¥ã£ãŠããå¿ èŠãããäºçŽæžã¿ã®ãã®ãããã€ããããŸãã
- iatïŒçºè¡æžã¿ïŒã ãã®ããŒã¯ãããŒã«ãŒãçºè¡ãããæéãè¡šããJWTã®å¹Žéœ¢ãå€æããããã«äœ¿çšã§ããŸãã iatããŒã¯ãUnix圢åŒã®ã¿ã€ã ã¹ã¿ã³ãã§ããå¿ èŠããããŸãã
- expïŒæå¹æéïŒã ãã®ããŒã¯ãããŒã¯ã³ã®æå¹æéã瀺ããŸãã æšæº
ãã€ããŒãã¯æå·åããã圢åŒã§ã¯éä¿¡ãããªãããšãç解ããããšãéèŠã§ãïŒãã ããããŒã¯ã³ããã¹ãããŠãæå·åãããããŒã¿ãéä¿¡ããããšã¯å¯èœã§ãïŒã ãããã£ãŠãç§å¯æ å ±ãä¿åããããšã¯ã§ããŸããã ããšãã°ããã¹ã¯ãŒãã瀟äŒä¿éçªå·ãªã©ã
ããããŒãšåæ§ã«ããã€ããŒãã¯base64ã§ãšã³ã³ãŒããããŸãã
眲å
ããããŒãšãã€ããŒããããã°ã眲åãèšç®ã§ããŸãã
Base64ã§ãšã³ã³ãŒãããããã®ãååŸãããŸããããããŒãšãã€ããŒãã¯ãããããä»ããŠ1è¡ã«çµåãããŸãã 次ã«ããã®è¡ãšç§å¯éµããããããŒã§æå®ãããæå·åã¢ã«ãŽãªãºã ã®å ¥åã«éä¿¡ãããŸãïŒããŒãalgãïŒã ããŒã«ã¯ä»»æã®æååã䜿çšã§ããŸãã äžèŽããã®ã«ããå€ãã®æéããããã®ã§ãé·ãæååãæãŸããã§ãããã
Jwt
ããããŒããã€ããŒããããã³çœ²åãã§ããã®ã§ãJWTãäœæã§ããŸãã æçµçãªJWTã¯æ¬¡ã®ãšããã§ãã
<encoded header>.<encoded payload>.<signature>
泚ïŒããŒã«ãŒãããŒã¿ããŒã¹ã«ä¿åããªãã§ãã ããã æå¹ãªããŒã¯ã³ã¯ãã¹ã¯ãŒããšåçã§ãããããããŒã¯ã³ã®ä¿åã¯ãã¹ã¯ãŒããã¯ãªã¢ããã¹ãã§ä¿åãããããªãã®ã§ãã ãããã£ãŠãä¿åããåã«å¿ ãããã·ã¥ã䜿çšããŠãã ããã
JSON Web TokenèªèšŒãå®è£ ãã
å ã«é²ãã§ãããžã§ã¯ããäœæããŸãããã
ãããžã§ã¯ããã£ã¬ã¯ããªã«ç§»åããã³ãã³ããå®è¡ããŸãã
$ django-admin.py startproject django_angular_token_auth $ cd django_angular_token_auth/ $ mkdir static templates
èšå®STATICFILES_DIRSããã³TEMPLATE_DIRSãdjango_angular_token_auth / settings.pyã«ååšãã次ã®ããã«ãªã£ãŠããããšã確èªããå¿ èŠããããŸãã
STATICFILES_DIRS = ( os.path.join(BASE_DIR, 'static'), ) TEMPLATE_DIRS = ( os.path.join(BASE_DIR, 'templates'), )
Django Rest Framework
次ã«ãDjango REST Frameworkãã€ã³ã¹ããŒã«ããå¿ èŠããããŸãã Django REST Frameworkã¯ãã·ã³ã°ã«ããŒãžã¢ããªã±ãŒã·ã§ã³ãšAPIãäœæããã人åãã®å€§èŠæš¡ãªãªãŒãã³ãœãŒã¹ãããžã§ã¯ãã§ãã
Django REST Frameworkã®ä»çµã¿ã«ã€ããŠã¯è©³ãã説æããŸããã®ã§ãåããŠäœ¿çšããå Žåã¯ããã¥ã¡ã³ããã芧ãã ããã
Django REST Frameworkãã€ã³ã¹ããŒã«ããã«ã¯ã次ã®ã³ãã³ããå®è¡ããŸãã
$ pip install djangorestframework
Django REST Frameworkãã€ã³ã¹ããŒã«æžã¿ã®ã¢ããªã±ãŒã·ã§ã³ã«è¿œå ããå¿ èŠããããŸãïŒdjango_angular_token_auth / settings.pyã®INSTALLED_APPS :)
INSTALLED_APPS = ( ..., 'rest_framework', )
ãŸãã次ã®ãã©ã¡ãŒã¿ãŒãdjango_angular_token_auth / settings.pyã«è¿œå ããå¿ èŠããããŸãã
REST_FRAMEWORK = { 'DEFAULT_PERMISSION_CLASSES': ( 'rest_framework.permissions.IsAuthenticated', ), 'DEFAULT_AUTHENTICATION_CLASSES': ( 'rest_framework.authentication.SessionAuthentication', 'rest_framework.authentication.BasicAuthentication', ), }
SessionAuthenticationãBasicAuthenticationã¯äœ¿çšããŸããããDjango REST Frameworkã§å©çšã§ããããã«äœ¿çšå¯èœãªAPIãæäŸããŸãã
django-rest-framework-jwt
æåŸã«è¡ãããšã¯ãdjango-rest-framework-jwtãã€ã³ã¹ããŒã«ããããšã§ãã ãã®ããã±ãŒãžã¯ãDjango REST Frameworkã®JWTãµããŒããæäŸããPyJWTå®è£ ãJSON WebããŒã¯ã³ãšããŠäœ¿çšããŸãã django-rest-framework-jwtãã€ã³ã¹ããŒã«ããã«ã¯ã次ã®ã³ãã³ããå®è¡ããŸãã
$ pip install djangorestframework-jwt
次ã®ãã©ã¡ãŒã¿ãŒãdjango_angular_token_auth / settings.pyã«è¿œå ããå¿ èŠããããŸãã
import datetime JWT_AUTH = { 'JWT_EXPIRATION_DELTA': datetime.timedelta(days=14) }
ãã®ãã©ã¡ãŒã¿ãŒã¯ãããŒã«ãŒã®å¯¿åœã瀺ãããã®å Žåã¯14æ¥éã§ãã ç¬èªã®èšå®ã«åºã¥ããŠå€æŽã§ããŸãã
æŽæ°ãããREST_FRAMEWORKèšå®ãè¿œå ããå¿ èŠããããŸãã
REST_FRAMEWORK = { 'DEFAULT_PERMISSION_CLASSES': ( 'rest_framework.permissions.IsAuthenticated', ), 'DEFAULT_AUTHENTICATION_CLASSES': ( 'rest_framework.authentication.SessionAuthentication', 'rest_framework.authentication.BasicAuthentication', 'rest_framework_jwt.authentication.JSONWebTokenAuthentication', ) }
è¿œå ããããšã«æ³šæããŠãã ããã
ãrest_framework_jwt.authentication.JSONWebTokenAuthenticationãããDEFAULT_AUTHENTICATION_CLASSESã
Djangoã¢ããªã±ãŒã·ã§ã³ã®äœæ
ããã§ã¯ããã¥ãŒãšã·ãªã¢ã©ã€ã¶ãŒãä¿åããDjangoã¢ããªã±ãŒã·ã§ã³ãäœæããŸãããã
$ python manage.py startapp authentication
ãèªèšŒããINSTALLED_APPSã«è¿œå ããŸãïŒdjango_angular_token_auth / settings.pyã®ããã«ïŒïŒ
INSTALLED_APPS = ( ..., 'rest_framework', 'authentication', )
ååãšããŠãã¢ããªã±ãŒã·ã§ã³ãäœæããåŸãããŒã¿ããŒã¹ã«ã¢ãã«ãäœæããããã«ç§»è¡ãå®è¡ããå¿ èŠããããŸãã ãã ããç¬èªã®ã¢ãã«ãäœæããããšã¯ãããŸããã®ã§ãããã«ã€ããŠå¿é ããå¿ èŠã¯ãããŸããã
ã·ãªã¢ã©ã€ã¶ãŒ
APIã®æ©èœã確èªããã«ã¯ãAJAXãªã¯ãšã¹ãã«ããŒã¿ãéä¿¡ããå¿ èŠããããŸãã ãããè¡ãæãç°¡åãªæ¹æ³ã¯ãã·ã¹ãã å ã®ãŠãŒã¶ãŒããŒã¿ãéãè¿ãããšã§ãã
æåã«è¡ãããšã¯ããŠãŒã¶ãŒã®äœæã§ãã 次ã®ã³ãã³ããå®è¡ããç»é¢ã®æ瀺ã«åŸããŸãã
$ python manage.py createsuperuser
ãŠãŒã¶ãŒãäœæããåŸãDjangoã¯èªåã®ããŒã¿ãAngularã¢ããªã±ãŒã·ã§ã³ã«éä¿¡ããå¿ èŠããããŸãã æããã«ãJavaScriptã§Djangoãªããžã§ã¯ããã¢ããªã±ãŒã·ã§ã³ã«éä¿¡ã§ããªãããããªããžã§ã¯ããJSONã«ããŸãã¯ãã®éã«å€æããã·ãªã¢ã©ã€ã¶ãŒãå¿ èŠã§ãã Django REST Frameworkã䜿çšããŠç°¡åã«äœæã§ããŸãã
serializers.pyãšãããã¡ã€ã«ãäœæãã次ã®ã³ãŒããè¿œå ããŸãã
from django.contrib.auth.models import User from rest_framework import serializers class UserSerializer(serializers.ModelSerializer): class Meta: model = User fields = (id, username, email)
ãã®ã³ãŒãã¯ãDjango REST Frameworkã«ããŠãŒã¶ãŒã¢ãã«ãã·ãªã¢ã«åããidãusernameãemailã®ãã£ãŒã«ãã®ã¿ãå«ããããšãæ瀺ããŸãã
èŠèŽåæ°
ã·ãªã¢ã©ã€ã¶ãŒãæŽçããããããã¥ãŒã«ç§»ããŸãããã
ãã®ç®çã®ããã«ããŠãŒã¶ãŒãªããžã§ã¯ãã®ãªã¹ããè¿ããã¥ãŒã1ã€ã ãå¿ èŠã§ãã
Django REST Frameworkã¯ãåãã¿ã€ãã®ãªããžã§ã¯ãã®ãªã¹ãã衚瀺ãããªã©ãããŸããŸãªæ©èœãå®è¡ããããŸããŸãªãã¥ãŒãæäŸããŸãã ãã®æ©èœã¯ãListAPIViewã¯ã©ã¹ã«ãã£ãŠæäŸãããŸãã
authentication / views.pyã«æ¬¡ãè¿œå ããŸãã
from django.contrib.auth.models import User from rest_framework import generics from authentication.serializers import UserSerializer class UserListAPIView(generics.ListAPIView): queryset = User.objects.all() serializer_class = UserSerializer
ãã¿ãŒã³
ã¢ããªã±ãŒã·ã§ã³ãè¡šãç°¡åãªãã³ãã¬ãŒããäœæããŸãããã
templates / index.htmlãšãããã¡ã€ã«ãäœæãã次ã®ã³ãŒããè¿œå ããŸãã
<!DOCTYPE html> <html> <head> <title>django-angular-token-auth</title> </head> <body> Hello, World! </body> </html>
å°æ¥ããã®ãã¡ã€ã«ã«è§åºŠã³ãŒããè¿œå ããŸãã
ãŠã«ã«
次ã«ããããžã§ã¯ãã®URLãæ§æããå¿ èŠããããŸãã
django_angular_token_auth / urls.pyãéãã次ã®ããã«ããŸãã
from django.conf.urls import include, patterns, url from django.views.generic import TemplateView from authentication.views import UserListAPIView urlpatterns = patterns('', url(r'api/v1/auth/login/', 'rest_framework_jwt.views.obtain_jwt_token'), url(r'api/v1/users/', UserListAPIView.as_view()), url(r'^.*$', TemplateView.as_view(template_name='index.html')), )
ããã§äœãèµ·ãã£ãŠããã®ãèŠãŠã¿ãŸãããã
æåã«æ°ä»ãããšãã§ããã®ã¯ãæåã®URLãã¿ãŒã³ã®2çªç®ã®åŒæ°ãæååã§ããããšã§ãã ãã®è¡ã¯ãããŒã¯ã³ãçæããdjango-rest-framework-jwtãã¥ãŒãæããŸãã ã©ã®ããã«æ©èœãããã¯èæ ®ããŸããããGithubãªããžããªã®django-rest-framework-jwtã³ãŒããèŠãããšãã§ããŸãïŒdjango-rest-framework-jwt / rest_framework_jwt / views.pyã
ãŸãã以åã«TemplateViewã䜿çšããŸããã§ããã Django REST Frameworkã®ListAPIViewã¯ã©ã¹ãšåæ§ã«ããã³ãã¬ãŒããåŠçããç°¡åãªæ¹æ³ãæäŸããŸãã
ãããããæåŸã®URLãã¿ãŒã³ã§äœ¿çšãããŠããæ£èŠè¡šçŸãã©ã®URLãšãäžèŽããããšã«æ°ã¥ããã§ãããã
é©åãªã¢ãã¬ã¹åŠçã®ããã«ããã®ãã³ãã¬ãŒããæåŸã§ããããšãéèŠã§ãã ãªããªããDjangoã¯å®çŸ©ãããé åºã§ã¢ãã¬ã¹ããã³ãã¬ãŒããšç §åããæåã®äžèŽã§ãã¹ããåæ¢ããããã§ãã 䜿çšãããæ£èŠè¡šçŸã¯ãã¹ãŠã®ã¢ãã¬ã¹ãšäžèŽãããããä»ã®ãã¹ãŠã®ã¢ãã¬ã¹ãåŠçãããæ©äŒãäžããŸãã Djangoã«æºæ ããŠããªããã®ã¯ãã¹ãŠãAngularã§åŠçããå¿ èŠããããŸãã ãŸããAPIåå空é/ api / v1 /ã¯ãDjangoãšAngularãã¿ãŒã³ã競åããªãããšãä¿èšŒããŸãã
第äºéš
åæ¢ããŸãã 2çªç®ã®éšåã§ã¯ãã¯ã©ã€ã¢ã³ãã¢ããªã±ãŒã·ã§ã³ãæ§ç¯ããäž»ã«ç»é²ãšãã°ã€ã³ã»ãã·ã§ã³ã«çŠç¹ãåœãŠãŸãã ã·ã¹ãã ãæ£ããéå§ããã³çµäºã§ããããã«ããµãŒãã¹ãäœæããŸãã