test(api): API Permission ViewSet Abstract Class added
ref: #15 #248 #345
This commit is contained in:
470
app/api/tests/abstract/api_permissions_viewset.py
Normal file
470
app/api/tests/abstract/api_permissions_viewset.py
Normal file
@ -0,0 +1,470 @@
|
|||||||
|
import pytest
|
||||||
|
import unittest
|
||||||
|
|
||||||
|
from django.shortcuts import reverse
|
||||||
|
from django.test import TestCase, Client
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
class APIPermissionView:
|
||||||
|
|
||||||
|
|
||||||
|
model: object
|
||||||
|
""" Item Model to test """
|
||||||
|
|
||||||
|
app_namespace: str = None
|
||||||
|
""" URL namespace """
|
||||||
|
|
||||||
|
url_name: str
|
||||||
|
""" URL name of the view to test """
|
||||||
|
|
||||||
|
url_view_kwargs: dict = None
|
||||||
|
""" URL kwargs of the item page """
|
||||||
|
|
||||||
|
|
||||||
|
def test_view_user_anon_denied(self):
|
||||||
|
""" Check correct permission for view
|
||||||
|
|
||||||
|
Attempt to view as anon user
|
||||||
|
"""
|
||||||
|
|
||||||
|
client = Client()
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-detail', kwargs=self.url_view_kwargs)
|
||||||
|
|
||||||
|
response = client.get(url)
|
||||||
|
|
||||||
|
assert response.status_code == 401
|
||||||
|
|
||||||
|
|
||||||
|
def test_view_no_permission_denied(self):
|
||||||
|
""" Check correct permission for view
|
||||||
|
|
||||||
|
Attempt to view with user missing permission
|
||||||
|
"""
|
||||||
|
|
||||||
|
client = Client()
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-detail', kwargs=self.url_view_kwargs)
|
||||||
|
|
||||||
|
|
||||||
|
client.force_login(self.no_permissions_user)
|
||||||
|
response = client.get(url)
|
||||||
|
|
||||||
|
assert response.status_code == 403
|
||||||
|
|
||||||
|
|
||||||
|
def test_view_different_organizaiton_denied(self):
|
||||||
|
""" Check correct permission for view
|
||||||
|
|
||||||
|
Attempt to view with user from different organization
|
||||||
|
"""
|
||||||
|
|
||||||
|
client = Client()
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-detail', kwargs=self.url_view_kwargs)
|
||||||
|
|
||||||
|
|
||||||
|
client.force_login(self.different_organization_user)
|
||||||
|
response = client.get(url)
|
||||||
|
|
||||||
|
assert response.status_code == 403
|
||||||
|
|
||||||
|
|
||||||
|
def test_view_has_permission(self):
|
||||||
|
""" Check correct permission for view
|
||||||
|
|
||||||
|
Attempt to view as user with view permission
|
||||||
|
"""
|
||||||
|
|
||||||
|
client = Client()
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-detail', kwargs=self.url_view_kwargs)
|
||||||
|
|
||||||
|
|
||||||
|
client.force_login(self.view_user)
|
||||||
|
response = client.get(url)
|
||||||
|
|
||||||
|
assert response.status_code == 200
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
class APIPermissionAdd:
|
||||||
|
|
||||||
|
|
||||||
|
model: object
|
||||||
|
""" Item Model to test """
|
||||||
|
|
||||||
|
app_namespace: str = None
|
||||||
|
""" URL namespace """
|
||||||
|
|
||||||
|
url_list: str
|
||||||
|
""" URL view name of the item list page """
|
||||||
|
|
||||||
|
url_kwargs: dict = None
|
||||||
|
""" URL view kwargs for the item list page """
|
||||||
|
|
||||||
|
add_data: dict = None
|
||||||
|
|
||||||
|
|
||||||
|
def test_add_user_anon_denied(self):
|
||||||
|
""" Check correct permission for add
|
||||||
|
|
||||||
|
Attempt to add as anon user
|
||||||
|
"""
|
||||||
|
|
||||||
|
client = Client()
|
||||||
|
if self.url_kwargs:
|
||||||
|
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-list', kwargs = self.url_kwargs)
|
||||||
|
|
||||||
|
else:
|
||||||
|
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-list')
|
||||||
|
|
||||||
|
|
||||||
|
response = client.put(url, data=self.add_data)
|
||||||
|
|
||||||
|
assert response.status_code == 401
|
||||||
|
|
||||||
|
# @pytest.mark.skip(reason="ToDO: figure out why fails")
|
||||||
|
def test_add_no_permission_denied(self):
|
||||||
|
""" Check correct permission for add
|
||||||
|
|
||||||
|
Attempt to add as user with no permissions
|
||||||
|
"""
|
||||||
|
|
||||||
|
client = Client()
|
||||||
|
if self.url_kwargs:
|
||||||
|
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-list', kwargs = self.url_kwargs)
|
||||||
|
|
||||||
|
else:
|
||||||
|
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-list')
|
||||||
|
|
||||||
|
|
||||||
|
client.force_login(self.no_permissions_user)
|
||||||
|
response = client.post(url, data=self.add_data)
|
||||||
|
|
||||||
|
assert response.status_code == 403
|
||||||
|
|
||||||
|
|
||||||
|
# @pytest.mark.skip(reason="ToDO: figure out why fails")
|
||||||
|
def test_add_different_organization_denied(self):
|
||||||
|
""" Check correct permission for add
|
||||||
|
|
||||||
|
attempt to add as user from different organization
|
||||||
|
"""
|
||||||
|
|
||||||
|
client = Client()
|
||||||
|
if self.url_kwargs:
|
||||||
|
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-list', kwargs = self.url_kwargs)
|
||||||
|
|
||||||
|
else:
|
||||||
|
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-list')
|
||||||
|
|
||||||
|
|
||||||
|
client.force_login(self.different_organization_user)
|
||||||
|
response = client.post(url, data=self.add_data)
|
||||||
|
|
||||||
|
assert response.status_code == 403
|
||||||
|
|
||||||
|
|
||||||
|
def test_add_permission_view_denied(self):
|
||||||
|
""" Check correct permission for add
|
||||||
|
|
||||||
|
Attempt to add a user with view permission
|
||||||
|
"""
|
||||||
|
|
||||||
|
client = Client()
|
||||||
|
if self.url_kwargs:
|
||||||
|
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-list', kwargs = self.url_kwargs)
|
||||||
|
|
||||||
|
else:
|
||||||
|
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-list')
|
||||||
|
|
||||||
|
|
||||||
|
client.force_login(self.view_user)
|
||||||
|
response = client.post(url, data=self.add_data)
|
||||||
|
|
||||||
|
assert response.status_code == 403
|
||||||
|
|
||||||
|
|
||||||
|
def test_add_has_permission(self):
|
||||||
|
""" Check correct permission for add
|
||||||
|
|
||||||
|
Attempt to add as user with permission
|
||||||
|
"""
|
||||||
|
|
||||||
|
client = Client()
|
||||||
|
if self.url_kwargs:
|
||||||
|
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-list', kwargs = self.url_kwargs)
|
||||||
|
|
||||||
|
else:
|
||||||
|
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-list')
|
||||||
|
|
||||||
|
|
||||||
|
client.force_login(self.add_user)
|
||||||
|
response = client.post(url, data=self.add_data)
|
||||||
|
|
||||||
|
assert response.status_code == 201
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
class APIPermissionChange:
|
||||||
|
|
||||||
|
|
||||||
|
model: object
|
||||||
|
""" Item Model to test """
|
||||||
|
|
||||||
|
app_namespace: str = None
|
||||||
|
""" URL namespace """
|
||||||
|
|
||||||
|
url_name: str
|
||||||
|
""" URL name of the view to test """
|
||||||
|
|
||||||
|
url_view_kwargs: dict = None
|
||||||
|
""" URL kwargs of the item page """
|
||||||
|
|
||||||
|
change_data: dict = None
|
||||||
|
|
||||||
|
|
||||||
|
def test_change_user_anon_denied(self):
|
||||||
|
""" Check correct permission for change
|
||||||
|
|
||||||
|
Attempt to change as anon
|
||||||
|
"""
|
||||||
|
|
||||||
|
client = Client()
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-detail', kwargs=self.url_view_kwargs)
|
||||||
|
|
||||||
|
|
||||||
|
response = client.patch(url, data=self.change_data, content_type='application/json')
|
||||||
|
|
||||||
|
assert response.status_code == 401
|
||||||
|
|
||||||
|
|
||||||
|
def test_change_no_permission_denied(self):
|
||||||
|
""" Ensure permission view cant make change
|
||||||
|
|
||||||
|
Attempt to make change as user without permissions
|
||||||
|
"""
|
||||||
|
|
||||||
|
client = Client()
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-detail', kwargs=self.url_view_kwargs)
|
||||||
|
|
||||||
|
|
||||||
|
client.force_login(self.no_permissions_user)
|
||||||
|
response = client.patch(url, data=self.change_data, content_type='application/json')
|
||||||
|
|
||||||
|
assert response.status_code == 403
|
||||||
|
|
||||||
|
|
||||||
|
def test_change_different_organization_denied(self):
|
||||||
|
""" Ensure permission view cant make change
|
||||||
|
|
||||||
|
Attempt to make change as user from different organization
|
||||||
|
"""
|
||||||
|
|
||||||
|
client = Client()
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-detail', kwargs=self.url_view_kwargs)
|
||||||
|
|
||||||
|
|
||||||
|
client.force_login(self.different_organization_user)
|
||||||
|
response = client.patch(url, data=self.change_data, content_type='application/json')
|
||||||
|
|
||||||
|
assert response.status_code == 403
|
||||||
|
|
||||||
|
|
||||||
|
def test_change_permission_view_denied(self):
|
||||||
|
""" Ensure permission view cant make change
|
||||||
|
|
||||||
|
Attempt to make change as user with view permission
|
||||||
|
"""
|
||||||
|
|
||||||
|
client = Client()
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-detail', kwargs=self.url_view_kwargs)
|
||||||
|
|
||||||
|
|
||||||
|
client.force_login(self.view_user)
|
||||||
|
response = client.patch(url, data=self.change_data, content_type='application/json')
|
||||||
|
|
||||||
|
assert response.status_code == 403
|
||||||
|
|
||||||
|
|
||||||
|
def test_change_permission_add_denied(self):
|
||||||
|
""" Ensure permission view cant make change
|
||||||
|
|
||||||
|
Attempt to make change as user with add permission
|
||||||
|
"""
|
||||||
|
|
||||||
|
client = Client()
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-detail', kwargs=self.url_view_kwargs)
|
||||||
|
|
||||||
|
|
||||||
|
client.force_login(self.add_user)
|
||||||
|
response = client.patch(url, data=self.change_data, content_type='application/json')
|
||||||
|
|
||||||
|
assert response.status_code == 403
|
||||||
|
|
||||||
|
|
||||||
|
def test_change_has_permission(self):
|
||||||
|
""" Check correct permission for change
|
||||||
|
|
||||||
|
Make change with user who has change permission
|
||||||
|
"""
|
||||||
|
|
||||||
|
client = Client()
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-detail', kwargs=self.url_view_kwargs)
|
||||||
|
|
||||||
|
|
||||||
|
client.force_login(self.change_user)
|
||||||
|
response = client.patch(url, data=self.change_data, content_type='application/json')
|
||||||
|
|
||||||
|
assert response.status_code == 200
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
class APIPermissionDelete:
|
||||||
|
|
||||||
|
|
||||||
|
model: object
|
||||||
|
""" Item Model to test """
|
||||||
|
|
||||||
|
app_namespace: str = None
|
||||||
|
""" URL namespace """
|
||||||
|
|
||||||
|
url_name: str
|
||||||
|
""" URL name of the view to test """
|
||||||
|
|
||||||
|
url_view_kwargs: dict = None
|
||||||
|
""" URL kwargs of the item page """
|
||||||
|
|
||||||
|
delete_data: dict = None
|
||||||
|
|
||||||
|
|
||||||
|
def test_delete_user_anon_denied(self):
|
||||||
|
""" Check correct permission for delete
|
||||||
|
|
||||||
|
Attempt to delete item as anon user
|
||||||
|
"""
|
||||||
|
|
||||||
|
client = Client()
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-detail', kwargs=self.url_view_kwargs)
|
||||||
|
|
||||||
|
|
||||||
|
response = client.delete(url, data=self.delete_data)
|
||||||
|
|
||||||
|
assert response.status_code == 401
|
||||||
|
|
||||||
|
|
||||||
|
def test_delete_no_permission_denied(self):
|
||||||
|
""" Check correct permission for delete
|
||||||
|
|
||||||
|
Attempt to delete as user with no permissons
|
||||||
|
"""
|
||||||
|
|
||||||
|
client = Client()
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-detail', kwargs=self.url_view_kwargs)
|
||||||
|
|
||||||
|
|
||||||
|
client.force_login(self.no_permissions_user)
|
||||||
|
response = client.delete(url, data=self.delete_data)
|
||||||
|
|
||||||
|
assert response.status_code == 403
|
||||||
|
|
||||||
|
|
||||||
|
def test_delete_different_organization_denied(self):
|
||||||
|
""" Check correct permission for delete
|
||||||
|
|
||||||
|
Attempt to delete as user from different organization
|
||||||
|
"""
|
||||||
|
|
||||||
|
client = Client()
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-detail', kwargs=self.url_view_kwargs)
|
||||||
|
|
||||||
|
|
||||||
|
client.force_login(self.different_organization_user)
|
||||||
|
response = client.delete(url, data=self.delete_data)
|
||||||
|
|
||||||
|
assert response.status_code == 403
|
||||||
|
|
||||||
|
|
||||||
|
def test_delete_permission_view_denied(self):
|
||||||
|
""" Check correct permission for delete
|
||||||
|
|
||||||
|
Attempt to delete as user with veiw permission only
|
||||||
|
"""
|
||||||
|
|
||||||
|
client = Client()
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-detail', kwargs=self.url_view_kwargs)
|
||||||
|
|
||||||
|
|
||||||
|
client.force_login(self.view_user)
|
||||||
|
response = client.delete(url, data=self.delete_data)
|
||||||
|
|
||||||
|
assert response.status_code == 403
|
||||||
|
|
||||||
|
|
||||||
|
def test_delete_permission_add_denied(self):
|
||||||
|
""" Check correct permission for delete
|
||||||
|
|
||||||
|
Attempt to delete as user with add permission only
|
||||||
|
"""
|
||||||
|
|
||||||
|
client = Client()
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-detail', kwargs=self.url_view_kwargs)
|
||||||
|
|
||||||
|
|
||||||
|
client.force_login(self.add_user)
|
||||||
|
response = client.delete(url, data=self.delete_data)
|
||||||
|
|
||||||
|
assert response.status_code == 403
|
||||||
|
|
||||||
|
|
||||||
|
def test_delete_permission_change_denied(self):
|
||||||
|
""" Check correct permission for delete
|
||||||
|
|
||||||
|
Attempt to delete as user with change permission only
|
||||||
|
"""
|
||||||
|
|
||||||
|
client = Client()
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-detail', kwargs=self.url_view_kwargs)
|
||||||
|
|
||||||
|
|
||||||
|
client.force_login(self.change_user)
|
||||||
|
response = client.delete(url, data=self.delete_data)
|
||||||
|
|
||||||
|
assert response.status_code == 403
|
||||||
|
|
||||||
|
|
||||||
|
def test_delete_has_permission(self):
|
||||||
|
""" Check correct permission for delete
|
||||||
|
|
||||||
|
Delete item as user with delete permission
|
||||||
|
"""
|
||||||
|
|
||||||
|
client = Client()
|
||||||
|
url = reverse(self.app_namespace + ':' + self.url_name + '-detail', kwargs=self.url_view_kwargs)
|
||||||
|
|
||||||
|
|
||||||
|
client.force_login(self.delete_user)
|
||||||
|
response = client.delete(url, data=self.delete_data)
|
||||||
|
|
||||||
|
assert response.status_code == 204
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
class APIPermissions(
|
||||||
|
APIPermissionAdd,
|
||||||
|
APIPermissionChange,
|
||||||
|
APIPermissionDelete,
|
||||||
|
APIPermissionView
|
||||||
|
):
|
||||||
|
""" Abstract class containing all API Permission test cases """
|
||||||
|
|
||||||
|
model: object
|
||||||
|
""" Item Model to test """
|
@ -1,11 +0,0 @@
|
|||||||
---
|
|
||||||
title: API Model Permission add Test Cases
|
|
||||||
description: No Fuss Computings model permissions add unit tests
|
|
||||||
date: 2024-06-16
|
|
||||||
template: project.html
|
|
||||||
about: https://gitlab.com/nofusscomputing/infrastructure/configuration-management/centurion_erp
|
|
||||||
---
|
|
||||||
|
|
||||||
::: app.api.tests.abstract.api_permissions.APIPermissionAdd
|
|
||||||
options:
|
|
||||||
show_source: true
|
|
@ -1,11 +0,0 @@
|
|||||||
---
|
|
||||||
title: Model Permissions Change Test Cases
|
|
||||||
description: No Fuss Computings model permissions change unit tests
|
|
||||||
date: 2024-06-15
|
|
||||||
template: project.html
|
|
||||||
about: https://gitlab.com/nofusscomputing/infrastructure/configuration-management/centurion_erp
|
|
||||||
---
|
|
||||||
|
|
||||||
::: app.api.tests.abstract.api_permissions.APIPermissionChange
|
|
||||||
options:
|
|
||||||
show_source: true
|
|
@ -1,11 +0,0 @@
|
|||||||
---
|
|
||||||
title: Model Permissions Delete Test Cases
|
|
||||||
description: No Fuss Computings model permissions delete unit tests
|
|
||||||
date: 2024-06-15
|
|
||||||
template: project.html
|
|
||||||
about: https://gitlab.com/nofusscomputing/infrastructure/configuration-management/centurion_erp
|
|
||||||
---
|
|
||||||
|
|
||||||
::: app.api.tests.abstract.api_permissions.APIPermissionDelete
|
|
||||||
options:
|
|
||||||
show_source: true
|
|
@ -1,11 +0,0 @@
|
|||||||
---
|
|
||||||
title: Model Permissions View Test Cases
|
|
||||||
description: No Fuss Computings model permissions view unit tests
|
|
||||||
date: 2024-06-15
|
|
||||||
template: project.html
|
|
||||||
about: https://gitlab.com/nofusscomputing/infrastructure/configuration-management/centurion_erp
|
|
||||||
---
|
|
||||||
|
|
||||||
::: app.api.tests.abstract.api_permissions.APIPermissionView
|
|
||||||
options:
|
|
||||||
show_source: true
|
|
@ -1,12 +0,0 @@
|
|||||||
---
|
|
||||||
title: API Model Permissions Test Cases
|
|
||||||
description: No Fuss Computings model permissions add unit tests
|
|
||||||
date: 2024-06-16
|
|
||||||
template: project.html
|
|
||||||
about: https://gitlab.com/nofusscomputing/infrastructure/configuration-management/centurion_erp
|
|
||||||
---
|
|
||||||
|
|
||||||
::: app.api.tests.abstract.api_permissions.APIPermissions
|
|
||||||
options:
|
|
||||||
show_source: true
|
|
||||||
inherited_members: true
|
|
@ -10,14 +10,36 @@ Unit tests are written to aid in application stability and to assist in preventi
|
|||||||
|
|
||||||
User Interface (UI) test are written _if applicable_ to test the user interface to ensure that it functions as it should. Changes to the UI will need to be tested.
|
User Interface (UI) test are written _if applicable_ to test the user interface to ensure that it functions as it should. Changes to the UI will need to be tested.
|
||||||
|
|
||||||
|
!!! note
|
||||||
|
As of release v1.3, the UI has moved to it's [own project](https://github.com/nofusscomputing/centurion_erp_ui) with the current Django UI feature locked and depreciated.
|
||||||
|
|
||||||
In most cases functional tests will not need to be written, however you should confirm this with a maintainer.
|
In most cases functional tests will not need to be written, however you should confirm this with a maintainer.
|
||||||
|
|
||||||
Integration tests **will** be required if the development introduces code that interacts with an independent third-party application.
|
Integration tests **will** be required if the development introduces code that interacts with an independent third-party application.
|
||||||
|
|
||||||
|
|
||||||
|
## Available Test classes
|
||||||
|
|
||||||
|
To aid in development we have written test classes that you can inherit from for your test classes
|
||||||
|
|
||||||
|
- API Permission Checks
|
||||||
|
|
||||||
|
_These tests ensure that only a user with the correct permissions can perform an action against a Model within Centurion_
|
||||||
|
|
||||||
|
- `api.tests.abstract.api_permissions_viewset.APIPermissionAdd` _Add permission checks_
|
||||||
|
|
||||||
|
- `api.tests.abstract.api_permissions_viewset.APIPermissionChange` _Change permission check_
|
||||||
|
|
||||||
|
- `api.tests.abstract.api_permissions_viewset.APIPermissionDelete` _Delete permission check_
|
||||||
|
|
||||||
|
- `api.tests.abstract.api_permissions_viewset.APIPermissionView` _View permission check_
|
||||||
|
|
||||||
|
- `api.tests.abstract.api_permissions_viewset.APIPermissions` _Add, Change, Delete and View permission checks_
|
||||||
|
|
||||||
|
|
||||||
## Writing Tests
|
## Writing Tests
|
||||||
|
|
||||||
We use class based tests. Each class will require a `setUpTestData` method for test setup. To furhter assist in the writing of tests, we have written the test cases for common items as an abstract class. You are advised to review the [test cases](./api/tests/index.md) and if it's applicable to the item you have added, than add the test case class to be inherited by your test class.
|
We use class based tests. Each class will require a `setUpTestData` method for test setup. To furhter assist in the writing of tests, we have written the test cases for common items as an abstract class. You are advised to inherit from our test classes _(see above)_ as a strating point and extend from there.
|
||||||
|
|
||||||
Naming of test classes is in `CamelCase` in format `<Model Name><what's being tested>` for example the class name for device model history entry tests would be `DeviceHistory`.
|
Naming of test classes is in `CamelCase` in format `<Model Name><what's being tested>` for example the class name for device model history entry tests would be `DeviceHistory`.
|
||||||
|
|
||||||
@ -30,7 +52,6 @@ Example of a model history test class.
|
|||||||
``` py
|
``` py
|
||||||
|
|
||||||
import pytest
|
import pytest
|
||||||
import unittest
|
|
||||||
import requests
|
import requests
|
||||||
|
|
||||||
from django.test import TestCase, Client
|
from django.test import TestCase, Client
|
||||||
@ -82,22 +103,19 @@ example file system structure showing the layout of the tests directory for a mo
|
|||||||
│ ├── test_<model name>_core_history.py
|
│ ├── test_<model name>_core_history.py
|
||||||
│ ├── test_<model name>_history_permission.py
|
│ ├── test_<model name>_history_permission.py
|
||||||
│ ├── test_<model name>.py
|
│ ├── test_<model name>.py
|
||||||
│ └── test_<model name>_views.py
|
│ └── test_<model name>_viewsets.py
|
||||||
|
|
||||||
```
|
```
|
||||||
|
|
||||||
Tests are broken up into the type the test is (sub-directory to test), and they are `unit`, `functional`, `UI` and `integration`. These sub-directories each contain a sub-directory for each model they are testing.
|
Tests are broken up into the type the test is (sub-directory to test), and they are `unit`, `functional`, `UI` and `integration`. These sub-directories each contain a sub-directory for each model they are testing.
|
||||||
|
|
||||||
|
|
||||||
Items to test include, and are not limited to:
|
Items to test include, and are not limited to:
|
||||||
|
|
||||||
- CRUD permissions admin site
|
- CRUD permissions admin site
|
||||||
|
|
||||||
- CRUD permissions api site - [ModelPermissions (API)](./api/tests/model_permissions_api.md)
|
- CRUD permissions api site
|
||||||
|
|
||||||
- CRUD permissions main site - [ModelPermissions](./api/tests/model_permissions.md)
|
- can only access organization object
|
||||||
|
|
||||||
- can only access organization object - [ModelPermissions](./api/tests/model_permissions.md), [ModelPermissions (API)](./api/tests/model_permissions_api.md)
|
|
||||||
|
|
||||||
- can access global object (still to require model CRUD permission)
|
- can access global object (still to require model CRUD permission)
|
||||||
|
|
||||||
|
10
mkdocs.yml
10
mkdocs.yml
@ -139,16 +139,6 @@ nav:
|
|||||||
|
|
||||||
- projects/centurion_erp/development/api/tests/model_permission_view_organization_manager.md
|
- projects/centurion_erp/development/api/tests/model_permission_view_organization_manager.md
|
||||||
|
|
||||||
- projects/centurion_erp/development/api/tests/model_permissions_api.md
|
|
||||||
|
|
||||||
- projects/centurion_erp/development/api/tests/model_permission_api_add.md
|
|
||||||
|
|
||||||
- projects/centurion_erp/development/api/tests/model_permission_api_change.md
|
|
||||||
|
|
||||||
- projects/centurion_erp/development/api/tests/model_permission_api_delete.md
|
|
||||||
|
|
||||||
- projects/centurion_erp/development/api/tests/model_permission_api_view.md
|
|
||||||
|
|
||||||
- projects/centurion_erp/development/api/tests/model_tenancy_object.md
|
- projects/centurion_erp/development/api/tests/model_tenancy_object.md
|
||||||
|
|
||||||
- projects/centurion_erp/development/api/tests/model_views.md
|
- projects/centurion_erp/development/api/tests/model_views.md
|
||||||
|
Reference in New Issue
Block a user