|
|
|
#!/usr/bin/env python
|
|
|
|
# -*- coding:utf-8 -*-
|
|
|
|
# project: 9月
|
|
|
|
# author: NinEveN
|
|
|
|
# date: 2020/9/24
|
|
|
|
import base64
|
|
|
|
|
|
|
|
from django.http.cookie import parse_cookie
|
|
|
|
from rest_framework.authentication import BaseAuthentication
|
|
|
|
from rest_framework.exceptions import AuthenticationFailed
|
|
|
|
from rest_framework.permissions import BasePermission
|
|
|
|
|
|
|
|
from api.models import UserInfo
|
|
|
|
from common.cache.storage import UserTokenCache
|
|
|
|
|
|
|
|
|
|
|
|
def get_cookie_token(request):
|
|
|
|
cookies = request.META.get('HTTP_COOKIE')
|
|
|
|
if cookies:
|
|
|
|
cookie_dict = parse_cookie(cookies)
|
|
|
|
return cookie_dict.get('auth_token')
|
|
|
|
|
|
|
|
|
|
|
|
def get_user_from_api_token(request):
|
|
|
|
if request.method == "OPTIONS":
|
|
|
|
return None
|
|
|
|
api_token = request.META.get("HTTP_APIAUTHORIZATION", request.query_params.get("api_token", None))
|
|
|
|
user_obj = UserInfo.objects.filter(api_token=api_token).first()
|
|
|
|
if not user_obj:
|
|
|
|
raise AuthenticationFailed({"code": 1001, "error": "无效的api_token"})
|
|
|
|
if user_obj.is_active:
|
|
|
|
return user_obj, api_token
|
|
|
|
else:
|
|
|
|
raise AuthenticationFailed({"code": 1001, "error": "用户被禁用"})
|
|
|
|
|
|
|
|
|
|
|
|
def get_user_from_request_auth(request):
|
|
|
|
if request.method == "OPTIONS":
|
|
|
|
return None
|
|
|
|
request_token = request.META.get("HTTP_AUTHORIZATION",
|
|
|
|
request.META.get("HTTP_X_TOKEN",
|
|
|
|
request.query_params.get("token", get_cookie_token(request))))
|
|
|
|
if request_token:
|
|
|
|
try:
|
|
|
|
format_token = base64.b64decode(request_token).decode()
|
|
|
|
auth_token = format_token.split(":")[0]
|
|
|
|
user_name = format_token.split(":")[1]
|
|
|
|
except Exception:
|
|
|
|
raise AuthenticationFailed({"code": 1001, "error": "token不合法"})
|
|
|
|
|
|
|
|
if not auth_token:
|
|
|
|
raise AuthenticationFailed({"code": 1001, "error": "缺少token"})
|
|
|
|
|
|
|
|
auth_cache = UserTokenCache(auth_token)
|
|
|
|
userinfo = auth_cache.get_storage_cache()
|
|
|
|
if not userinfo:
|
|
|
|
raise AuthenticationFailed({"code": 1001, "error": "无效的token"})
|
|
|
|
if user_name != userinfo.get('username', None):
|
|
|
|
raise AuthenticationFailed({"code": 1001, "error": "token校验失败"})
|
|
|
|
|
|
|
|
user_obj = UserInfo.objects.filter(uid=userinfo.get('uid', None),
|
|
|
|
username=userinfo.get("username")).first()
|
|
|
|
if not user_obj:
|
|
|
|
raise AuthenticationFailed({"code": 1001, "error": "无效的token"})
|
|
|
|
if user_obj.is_active:
|
|
|
|
auth_cache.set_storage_cache(userinfo, 3600 * 24 * 7)
|
|
|
|
return user_obj, auth_token
|
|
|
|
else:
|
|
|
|
raise AuthenticationFailed({"code": 1001, "error": "用户被禁用"})
|
|
|
|
else:
|
|
|
|
raise AuthenticationFailed({"code": 1001, "error": "无效的认证"})
|
|
|
|
|
|
|
|
|
|
|
|
class ExpiringTokenAuthentication(BaseAuthentication):
|
|
|
|
|
|
|
|
def authenticate(self, request):
|
|
|
|
return get_user_from_request_auth(request)
|
|
|
|
|
|
|
|
|
|
|
|
class AdminTokenAuthentication(BaseAuthentication):
|
|
|
|
|
|
|
|
def authenticate(self, request):
|
|
|
|
result = get_user_from_request_auth(request)
|
|
|
|
if result:
|
|
|
|
user_obj, token = result
|
|
|
|
if user_obj and user_obj.role == 3:
|
|
|
|
return result
|
|
|
|
else:
|
|
|
|
raise AuthenticationFailed({"code": 1001, "error": "无效的认证"})
|
|
|
|
return result
|
|
|
|
|
|
|
|
|
|
|
|
class ApiTokenAuthentication(BaseAuthentication):
|
|
|
|
|
|
|
|
def authenticate(self, request):
|
|
|
|
return get_user_from_api_token(request)
|
|
|
|
|
|
|
|
|
|
|
|
class StoragePermission(BasePermission):
|
|
|
|
message = "权限不足"
|
|
|
|
|
|
|
|
def has_permission(self, request, view):
|
|
|
|
results = get_user_from_request_auth(request)
|
|
|
|
if results and results[0]:
|
|
|
|
return results[0].storage_active
|
|
|
|
return True
|
|
|
|
|
|
|
|
|
|
|
|
class SuperSignPermission(BasePermission):
|
|
|
|
message = "权限不足"
|
|
|
|
|
|
|
|
def has_permission(self, request, view):
|
|
|
|
results = get_user_from_request_auth(request)
|
|
|
|
if results and results[0]:
|
|
|
|
return results[0].supersign_active
|
|
|
|
return True
|
|
|
|
|
|
|
|
|
|
|
|
class DownloadQrPermission(BasePermission):
|
|
|
|
message = "权限不足"
|
|
|
|
|
|
|
|
def has_permission(self, request, view):
|
|
|
|
domain_type = request.query_params.get('domain_type', -1)
|
|
|
|
results = get_user_from_request_auth(request)
|
|
|
|
if results and results[0]:
|
|
|
|
if domain_type == '0' and results[0].role < 2:
|
|
|
|
return False
|
|
|
|
return True
|
|
|
|
|
|
|
|
|
|
|
|
class UserAdInfoPermission(BasePermission):
|
|
|
|
message = "权限不足"
|
|
|
|
|
|
|
|
def has_permission(self, request, view):
|
|
|
|
results = get_user_from_request_auth(request)
|
|
|
|
if results and results[0]:
|
|
|
|
if results[0].role < 2:
|
|
|
|
return False
|
|
|
|
return True
|