Xây dựng nhanh chóng API với Django Tastypie [Phần 2]
Bài đăng này đã không được cập nhật trong 6 năm
Tiếp theo trong series tutorial về Django Tastypie, mình sẽ giới thiệu thêm toàn bộ trong phần Authentication: Khuyến nghị bạn nên đọc trước phần 1 tại đây để tránh một vài điều không hiểu
Authentication là một component cần thiết đề xác thực ai và quyền hạn của họ truy câp tới một API nào đó.
Usage
Cơ bản nhất là thêm option authentication
vào trong class Meta
của resource.py
Ở đây mình setup thêm BasicAuthentication
cho API này
from django.contrib.auth.models import User
from tastypie.authentication import BasicAuthentication
from tastypie.resources import ModelResource
class UserResource(ModelResource):
class Meta:
queryset = User.objects.all()
resource_name = 'auth/user'
excludes = ['email', 'password', 'is_superuser']
# Add it here.
authentication = BasicAuthentication
Đây là kết quả
Options
Ngoài BasicAuthentication
Tastypie cung cấp một số Auth khác
Authentication
Đây là option mặc định của Tastypie. Client luôn luôn có thể truy cập vào API. Cái này rất hữu ích cho việc develop
BasicAuthentication
Đây là option cho phép setup một HTTP Basic Auth cơ bản. Username/password chính là dữ liệu được save trong django.contrib.auth.models.User
.
Một lưu ý khi dùng BasicAuthentication
kết hợp với Apache
và mod_wsgi
đó là phải enable WSGIPassAuthorization
.
ApiKeyAuthentication
Đây là option cho phép thay thế sự auth password bằng một mã api_key
. ApiKeyAuthentication
cung cấp một machine-generated
cho phép genrerated từ username/password ra một mã api_key
.
Có 2 cách để làm việc này:
- Setup một signal để mỗi khi tạo một User sẽ tự sinh ra một
api_key
from django.contrib.auth.models import User
from django.db.models import signals
from tastypie.models import create_api_key
signals.post_save.connect(create_api_key, sender=User)
- Với những data user cũ:
$python manage.py backfill_api_keys
Created a new key for 'minhhahao'
Created a new key for 'ha.hao.minh'
Created a new key for 'nguyen.thi.van'
Kiếm tra bảng tastypie_apikey
:
Để sử dụng nó mình cần sửa lại code trong phần authentication
- tất nhiên rồi =)):
# resources.py
from tastypie.resources import ModelResource
from tastypie.authentication import ApiKeyAuthentication
from django.contrib.auth.models import User
class AccountResource(ModelResource):
class Meta:
queryset = User.objects.all()
allowed_methods = ['get']
excludes = ['email', 'password', 'is_superuser']
authentication = ApiKeyAuthentication()
Thêm vào Header Authorization theo cấu trúc:
Authorization: ApiKey <username>:<api_key>
Kết quả:
SessionAuthentication
Đây là option auth dựa trên Django session. Vậy nên mình cũng không muốn nói gì thế :v Nếu bạn không hiểu bạn có thể đọc thêm về Django session tại đây
DigestAuthentication
Đây là option cho phép setup một HTTP Digest Auth. Cái này tương tự BasicAuthentication
.Tuy nhiên, bạn phải cài đặt thêm gói python_digest
Mình có thể cài gói này qua pip:
$pip install python_digest
Collecting python_digest
Downloading https://files.pythonhosted.org/packages/8a/24/e5d9e5a4b4cf2ff5952e847e814303c31967226bd7bae89ee061e1f0c674/python-digest-1.7.tar.gz
Building wheels for collected packages: python-digest
Running setup.py bdist_wheel for python-digest ... done
Stored in directory: /Users/minhhahao/Library/Caches/pip/wheels/5f/be/90/1f6cfa54c783455991ecc42937828075a9606b93ca43defd4b
Successfully built python-digest
Installing collected packages: python-diges
Ok
OAuthAuthentication
Đây là option handle OAuth.
MultiAuthentication
Đây là option cho phép kết hợp nhiều option auth.
Ví dụ:
from django.contrib.auth.models import User
from tastypie.authentication import BasicAuthentication, ApiKeyAuthentication, MultiAuthentication
from tastypie.authorization import DjangoAuthorization
from tastypie.resources import ModelResource
class UserResource(ModelResource):
class Meta:
queryset = User.objects.all()
resource_name = 'auth/user'
excludes = ['email', 'password', 'is_superuser']
authentication = MultiAuthentication(BasicAuthentication(), ApiKeyAuthentication())
authorization = DjangoAuthorization()
Ở ví dụ trên, API này có thể auth bằng 2 cách:
- Auth bằng
BasicAuthentication
nếu người dùng chỉ có username/password - Auth bằng
ApiKeyAuthentication
nếu người dùng muốn sử dụngapi_key
Đây mình đánh giá là option rất là hay của Tastypie
Implementing a your Authentication
Bạn hoàn toàn có thể tự tạo ra một Class để auth theo cách bạn muốn. Cái này mình recommend là bạn nên sử dụng để phù hợp với từng dự án
Đây là một ví dụ:
from tastypie.authentication import Authentication
class ApiAcountOptionAuthentication(Authentication):
def is_authenticated(self, request, **kwargs):
if request.user.is_authenticated():
return True
try:
if "HTTP_TOKEN" in request.META:
access_token = request.META.get('HTTP_TOKEN')
if access_token:
user = get_user_profile_service().get_api_user_from_token(token=access_token)
request.user = user
if "HTTP_AUTHORIZATION" in request.META:
access_token = request.META.get('HTTP_AUTHORIZATION')
if "Bearer" in access_token:
valid, r = get_oauthlib_core().verify_request(request, scopes=[])
if valid:
request.user = r.user
except Exception as ex:
request.user = None
return True
...
Tới đây bài viết cũng hết rồi. Một vài lưu ý nhỏ với các bạn là với những server sử dụng Apache và mod_wsgi
, những auth option sau sẽ phải enable WSGIPassAuthorization
:
- DigestAuthentication
- BasicAuthentication
- ApiKeyAuthentication
Thanks for reading
All rights reserved