#31 API Tests
* writes test for sharing using the API * fixes bug on frontend form where an exception occured on generating a new API token if no token existed, yet * adds permission constraint (default group) for using the api in general * fixes default-group-only behaviour for sharing-API, so users can only add new users and not removing them, as long as they do not have any other group membership like registration or conservation office * changes 'ksptoken' to 'Ksptoken' to match CGI standard for http header keyspull/90/head
parent
b86202ba98
commit
8f40162974
@ -1,3 +0,0 @@
|
||||
from django.test import TestCase
|
||||
|
||||
# Create your tests here.
|
@ -0,0 +1,7 @@
|
||||
"""
|
||||
Author: Michel Peltriaux
|
||||
Organization: Struktur- und Genehmigungsdirektion Nord, Rhineland-Palatinate, Germany
|
||||
Contact: michel.peltriaux@sgdnord.rlp.de
|
||||
Created on: 27.01.22
|
||||
|
||||
"""
|
@ -0,0 +1,150 @@
|
||||
import json
|
||||
|
||||
from django.urls import reverse
|
||||
|
||||
from konova.settings import DEFAULT_GROUP
|
||||
from konova.tests.test_views import BaseTestCase
|
||||
from konova.utils.user_checks import is_default_group_only
|
||||
|
||||
|
||||
class APIV1SharingTestCase(BaseTestCase):
|
||||
|
||||
@classmethod
|
||||
def setUpTestData(cls):
|
||||
""" Creates a test file in memory for using in further tests
|
||||
|
||||
Returns:
|
||||
|
||||
"""
|
||||
super().setUpTestData()
|
||||
cls.superuser.get_API_token()
|
||||
cls.superuser.api_token.is_active = True
|
||||
cls.superuser.api_token.save()
|
||||
default_group = cls.groups.get(name=DEFAULT_GROUP)
|
||||
cls.superuser.groups.add(default_group)
|
||||
|
||||
cls.header_data = {
|
||||
"HTTP_ksptoken": cls.superuser.api_token.token,
|
||||
}
|
||||
|
||||
def _run_share_request(self, url, user_list: list):
|
||||
data = {
|
||||
"users": user_list
|
||||
}
|
||||
data = json.dumps(data)
|
||||
response = self.client.put(
|
||||
url,
|
||||
data,
|
||||
**self.header_data
|
||||
)
|
||||
return response
|
||||
|
||||
def _test_api_sharing(self, obj, url):
|
||||
""" Generic test for testing sharing of a ShareableObjectMixin object
|
||||
|
||||
Args:
|
||||
obj (ShareableObjectMixin): The object
|
||||
url (str): The url to be used for a request
|
||||
|
||||
Returns:
|
||||
|
||||
"""
|
||||
self.assertEqual(obj.users.count(), 0)
|
||||
user_list = [
|
||||
self.superuser.username,
|
||||
self.user.username,
|
||||
]
|
||||
|
||||
response = self._run_share_request(url, user_list)
|
||||
|
||||
# Must fail, since performing user has no access on requested object
|
||||
self.assertEqual(response.status_code, 500)
|
||||
self.assertTrue(len(json.loads(response.content.decode("utf-8")).get("errors", [])) > 0)
|
||||
|
||||
# Add performing user to shared access users and rerun the request
|
||||
obj.users.add(self.superuser)
|
||||
response = self._run_share_request(url, user_list)
|
||||
|
||||
shared_users = obj.shared_users
|
||||
self.assertEqual(response.status_code, 200)
|
||||
self.assertEqual(shared_users.count(), 2)
|
||||
self.assertIn(self.superuser, shared_users)
|
||||
self.assertIn(self.user, shared_users)
|
||||
|
||||
def test_api_token_invalid(self):
|
||||
""" Tests that a request with an invalid token won't be successfull
|
||||
|
||||
Returns:
|
||||
|
||||
"""
|
||||
share_url = reverse("api:v1:intervention-share", args=(self.intervention.id,))
|
||||
# Expect the first request to work properly
|
||||
self.intervention.users.add(self.superuser)
|
||||
response = self._run_share_request(share_url, [self.superuser.username])
|
||||
self.assertEqual(response.status_code, 200)
|
||||
|
||||
# Change the token
|
||||
self.header_data["HTTP_ksptoken"] = f"{self.superuser.api_token.token}__X"
|
||||
|
||||
# Expect the request to fail now
|
||||
response = self._run_share_request(share_url, [self.superuser.username])
|
||||
self.assertEqual(response.status_code, 403)
|
||||
|
||||
def test_api_intervention_sharing(self):
|
||||
""" Tests proper sharing of intervention
|
||||
|
||||
Returns:
|
||||
|
||||
"""
|
||||
share_url = reverse("api:v1:intervention-share", args=(self.intervention.id,))
|
||||
self._test_api_sharing(self.intervention, share_url)
|
||||
|
||||
def test_api_eco_account_sharing(self):
|
||||
""" Tests proper sharing of eco account
|
||||
|
||||
Returns:
|
||||
|
||||
"""
|
||||
share_url = reverse("api:v1:ecoaccount-share", args=(self.eco_account.id,))
|
||||
self._test_api_sharing(self.eco_account, share_url)
|
||||
|
||||
def test_api_ema_sharing(self):
|
||||
""" Tests proper sharing of ema
|
||||
|
||||
Returns:
|
||||
|
||||
"""
|
||||
share_url = reverse("api:v1:ema-share", args=(self.ema.id,))
|
||||
self._test_api_sharing(self.ema, share_url)
|
||||
|
||||
def test_api_sharing_as_default_group_only(self):
|
||||
""" Tests that sharing using the API as an only default group user works as expected.
|
||||
|
||||
Expected:
|
||||
Default only user can only add new users, having shared access. Removing them from the list of users
|
||||
having shared access is only possible if the user has further rights, e.g. being part of a registration
|
||||
or conservation office group.
|
||||
|
||||
Returns:
|
||||
|
||||
"""
|
||||
share_url = reverse("api:v1:intervention-share", args=(self.intervention.id,))
|
||||
|
||||
# Give the user only default group rights
|
||||
default_group = self.groups.get(name=DEFAULT_GROUP)
|
||||
self.superuser.groups.set([default_group])
|
||||
self.assertTrue(is_default_group_only(self.superuser))
|
||||
|
||||
# Add only him as shared_users an object
|
||||
self.intervention.users.set([self.superuser])
|
||||
self.assertEqual(self.intervention.users.count(), 1)
|
||||
|
||||
# Try to add another user via API -> must work!
|
||||
response = self._run_share_request(share_url, [self.superuser.username, self.user.username])
|
||||
self.assertEqual(response.status_code, 200)
|
||||
self.assertEqual(self.intervention.users.count(), 2)
|
||||
|
||||
# Now try to remove the user again -> expect no changes at all to the shared user list
|
||||
response = self._run_share_request(share_url, [self.superuser.username])
|
||||
self.assertEqual(response.status_code, 200)
|
||||
self.assertEqual(self.intervention.users.count(), 2)
|
Loading…
Reference in New Issue