1import logging 2 3from rest_framework import status 4from rest_framework.authentication import SessionAuthentication 5from rest_framework.permissions import IsAuthenticated 6from rest_framework.response import Response 7from rest_framework.views import APIView 8 9from django.utils.translation import ugettext as _ 10 11from seahub.api2.authentication import TokenAuthentication 12from seahub.api2.throttling import UserRateThrottle 13from seahub.api2.utils import api_error 14 15from seaserv import seafile_api 16 17from seahub.constants import PERMISSION_READ_WRITE 18from seahub.repo_api_tokens.models import RepoAPITokens 19from seahub.repo_api_tokens.utils import permission_check_admin_owner 20 21logger = logging.getLogger(__name__) 22 23 24def _get_repo_token_info(repo_token_obj): 25 return { 26 'repo_id': repo_token_obj.repo_id, 27 'app_name': repo_token_obj.app_name, 28 'generated_by': repo_token_obj.generated_by, 29 'permission': repo_token_obj.permission, 30 'api_token': repo_token_obj.token 31 } 32 33 34class RepoAPITokensView(APIView): 35 authentication_classes = (TokenAuthentication, SessionAuthentication) 36 permission_classes = (IsAuthenticated,) 37 throttle_classes = (UserRateThrottle,) 38 39 def get(self, request, repo_id): 40 # resource check 41 repo = seafile_api.get_repo(repo_id) 42 if not repo: 43 error_msg = 'Library %(repo_id)s not found.' % {'repo_id': repo_id} 44 return api_error(status.HTTP_404_NOT_FOUND, error_msg) 45 46 # permission check 47 username = request.user.username 48 if not permission_check_admin_owner(request, username, repo_id): 49 error_msg = 'Permission denied.' 50 return api_error(status.HTTP_403_FORBIDDEN, error_msg) 51 52 rats = RepoAPITokens.objects.filter(repo_id=repo_id).order_by('-generated_at') 53 rat_infos = [_get_repo_token_info(rat) for rat in rats] 54 return Response({'repo_api_tokens': rat_infos}) 55 56 def post(self, request, repo_id): 57 # arguments check 58 app_name = request.data.get('app_name') 59 if not app_name: 60 error_msg = 'app_name invalid.' 61 return api_error(status.HTTP_400_BAD_REQUEST, error_msg) 62 repo_permission = request.data.get('permission') 63 if repo_permission and repo_permission not in [perm[0] for perm in RepoAPITokens.PERMISSION_CHOICES]: 64 error_msg = 'permission invalid.' 65 return api_error(status.HTTP_400_BAD_REQUEST, error_msg) 66 repo_permission = repo_permission if repo_permission else PERMISSION_READ_WRITE 67 68 # resource check 69 repo = seafile_api.get_repo(repo_id) 70 if not repo: 71 error_msg = 'Library %(repo_id)s not found.' % {'repo_id': repo_id} 72 return api_error(status.HTTP_404_NOT_FOUND, error_msg) 73 74 # permission check 75 username = request.user.username 76 if not permission_check_admin_owner(request, username, repo_id): 77 error_msg = 'Permission denied.' 78 return api_error(status.HTTP_403_FORBIDDEN, error_msg) 79 80 rat = RepoAPITokens.objects.filter(app_name=app_name, repo_id=repo_id).first() 81 if rat: 82 error_msg = 'app: %(app)s token already exists.' % {'app': app_name} 83 return api_error(status.HTTP_400_BAD_REQUEST, error_msg) 84 try: 85 rat = RepoAPITokens.objects.create_token(app_name=app_name, 86 repo_id=repo_id, 87 username=username, 88 permission=repo_permission) 89 except Exception as e: 90 logger.error('user: %s create repo: %s\'s token error: %s', username, repo_id, e) 91 error_msg = 'Internal Server Error' 92 return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR, error_msg) 93 94 return Response(_get_repo_token_info(rat)) 95 96 97class RepoAPITokenView(APIView): 98 authentication_classes = (TokenAuthentication, SessionAuthentication) 99 permission_classes = (IsAuthenticated,) 100 throttle_classes = (UserRateThrottle,) 101 102 def delete(self, request, repo_id, app_name): 103 # resource check 104 repo = seafile_api.get_repo(repo_id) 105 if not repo: 106 error_msg = 'Library %(repo_id)s not found.' % {'repo_id': repo_id} 107 return api_error(status.HTTP_404_NOT_FOUND, error_msg) 108 109 username = request.user.username 110 # permission check 111 if not permission_check_admin_owner(request, username, repo_id): 112 error_msg = 'Permission denied.' 113 return api_error(status.HTTP_403_FORBIDDEN, error_msg) 114 115 try: 116 rat = RepoAPITokens.objects.filter(repo_id=repo_id, app_name=app_name).first() 117 if not rat: 118 error_msg = 'api token not found' 119 return api_error(status.HTTP_404_NOT_FOUND, error_msg) 120 rat.delete() 121 except Exception as e: 122 logger.error('user: %s delete repo: %s app_name: %s error: %s', username, repo_id, app_name, e) 123 error_msg = 'Internal Server Error' 124 return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR, error_msg) 125 return Response({'success': True}) 126 127 def put(self, request, repo_id, app_name): 128 # arguments check 129 permission = request.data.get('permission') 130 if not permission or permission not in [perm[0] for perm in RepoAPITokens.PERMISSION_CHOICES]: 131 error_msg = 'permission invalid.' 132 return api_error(status.HTTP_400_BAD_REQUEST, error_msg) 133 134 # resource check 135 repo = seafile_api.get_repo(repo_id) 136 if not repo: 137 error_msg = 'Library %(repo_id)s not found.' % {'repo_id': repo_id} 138 return api_error(status.HTTP_404_NOT_FOUND, error_msg) 139 140 # permission check 141 username = request.user.username 142 if not permission_check_admin_owner(request, username, repo_id): 143 error_msg = 'Permission denied.' 144 return api_error(status.HTTP_403_FORBIDDEN, error_msg) 145 146 rat = RepoAPITokens.objects.filter(app_name=app_name, repo_id=repo_id).first() 147 if not rat: 148 error_msg = 'api token not found' 149 return api_error(status.HTTP_404_NOT_FOUND, error_msg) 150 151 try: 152 rat.permission = permission 153 rat.save() 154 except Exception as e: 155 logger.error('user: %s update repo: %s app_name: %s error: %s', username, repo_id, app_name, e) 156 error_msg = 'Internal Server Error' 157 return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR, error_msg) 158 159 return Response(_get_repo_token_info(rat)) 160