提交 876784eb 编写于 作者: N Nikita Manovich

Merge remote-tracking branch 'origin/develop' into release-2.0.0

......@@ -260,7 +260,7 @@ class ProjectViewSet(viewsets.ModelViewSet):
ordering_fields = filter_fields
ordering = "-id"
lookup_fields = {'owner': 'owner__username', 'assignee': 'assignee__username'}
http_method_names = ('get', 'post', 'head', 'patch', 'delete')
http_method_names = ('get', 'post', 'head', 'patch', 'delete', 'options')
iam_organization_field = 'organization'
def get_serializer_class(self):
......@@ -1243,7 +1243,7 @@ class CommentViewSet(viewsets.ModelViewSet):
class UserViewSet(viewsets.GenericViewSet, mixins.ListModelMixin,
mixins.RetrieveModelMixin, mixins.UpdateModelMixin, mixins.DestroyModelMixin):
queryset = User.objects.prefetch_related('groups').all()
http_method_names = ['get', 'post', 'head', 'patch', 'delete']
http_method_names = ['get', 'post', 'head', 'patch', 'delete', 'options']
search_fields = ('username', 'first_name', 'last_name')
iam_organization_field = 'memberships__organization'
......@@ -1313,7 +1313,7 @@ class UserViewSet(viewsets.GenericViewSet, mixins.ListModelMixin,
'201': CloudStorageWriteSerializer,
}, tags=['cloud storages'], versions=['2.0']))
class CloudStorageViewSet(viewsets.ModelViewSet):
http_method_names = ['get', 'post', 'patch', 'delete']
http_method_names = ['get', 'post', 'patch', 'delete', 'options']
queryset = CloudStorageModel.objects.all().prefetch_related('data')
search_fields = ('provider_type', 'display_name', 'resource',
......
......@@ -1015,8 +1015,14 @@ class PolicyEnforcer(BasePermission):
# pylint: disable=no-self-use
def check_permission(self, request, view, obj):
permissions = []
for perm in OpenPolicyAgentPermission.__subclasses__():
permissions.extend(perm.create(request, view, obj))
# DRF can send OPTIONS request. Internally it will try to get
# information about serializers for PUT and POST requests (clone
# request and replace the http method). To avoid handling
# ('POST', 'metadata') and ('PUT', 'metadata') in every request,
# the condition below is enough.
if not self.is_metadata_request(request, view):
for perm in OpenPolicyAgentPermission.__subclasses__():
permissions.extend(perm.create(request, view, obj))
return all(permissions)
......@@ -1029,6 +1035,10 @@ class PolicyEnforcer(BasePermission):
def has_object_permission(self, request, view, obj):
return self.check_permission(request, view, obj)
@staticmethod
def is_metadata_request(request, view):
return request.method == 'OPTIONS' or view.action == 'metadata'
class IsMemberInOrganization(BasePermission):
message = 'You should be an active member in the organization.'
......
......@@ -4,9 +4,35 @@
from http import HTTPStatus
import pytest
from .utils.config import get_method, patch_method, delete_method
from .utils.config import get_method, options_method, patch_method, delete_method
from deepdiff import DeepDiff
class TestMetadataOrganizations:
_ORG = 2
@pytest.mark.parametrize('privilege, role, is_member', [
('admin', None, None),
('user', None, False),
('business', None, False),
('worker', None, False),
(None, 'owner', True),
(None, 'maintainer', True),
(None, 'worker', True),
(None, 'supervisor', True),
])
def test_can_send_options_request(self, privilege, role, is_member,
find_users, organizations):
exclude_org = None if is_member else self._ORG
org = self._ORG if is_member else None
user = find_users(privilege=privilege, role=role, org=org,
exclude_org=exclude_org)[0]['username']
response = options_method(user, f'organizations')
assert response.status_code == HTTPStatus.OK
response = options_method(user, f'organizations/{self._ORG}')
assert response.status_code == HTTPStatus.OK
class TestGetOrganizations:
_ORG = 2
......
......@@ -24,6 +24,9 @@ def get_api_url(endpoint, **kwargs):
def get_method(username, endpoint, **kwargs):
return requests.get(get_api_url(endpoint, **kwargs), auth=(username, USER_PASS))
def options_method(username, endpoint, **kwargs):
return requests.options(get_api_url(endpoint, **kwargs), auth=(username, USER_PASS))
def delete_method(username, endpoint, **kwargs):
return requests.delete(get_api_url(endpoint, **kwargs), auth=(username, USER_PASS))
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册