commit
b05c6c81d6
8
.flake8
8
.flake8
|
@ -1,8 +0,0 @@
|
||||||
[flake8]
|
|
||||||
exclude =
|
|
||||||
*migrations*,
|
|
||||||
__init__.py,
|
|
||||||
*cache*,
|
|
||||||
venv/,
|
|
||||||
src/manage.py,
|
|
||||||
src/network_inventory/settings/*
|
|
|
@ -51,7 +51,7 @@
|
||||||
pkgs.python310Packages.pip
|
pkgs.python310Packages.pip
|
||||||
(pkgs.writeScriptBin "dev" "${builtins.readFile ./dev.sh}")
|
(pkgs.writeScriptBin "dev" "${builtins.readFile ./dev.sh}")
|
||||||
];
|
];
|
||||||
PYTHON_KEYRING_BACKEND="keyring.backends.fail.Keyring";
|
PYTHON_KEYRING_BACKEND = "keyring.backends.fail.Keyring";
|
||||||
shellHook = ''
|
shellHook = ''
|
||||||
export DJANGO_SETTINGS_MODULE=network_inventory.settings.local
|
export DJANGO_SETTINGS_MODULE=network_inventory.settings.local
|
||||||
'';
|
'';
|
||||||
|
@ -68,8 +68,10 @@
|
||||||
checkInputs = [ pkgs.inventoryDevEnv ];
|
checkInputs = [ pkgs.inventoryDevEnv ];
|
||||||
checkPhase = ''
|
checkPhase = ''
|
||||||
mkdir -p $out
|
mkdir -p $out
|
||||||
flake8 . --count --show-source --statistics
|
pylint --rc-file pyproject.toml -j 0 -E src/
|
||||||
|
cd src/ && mypy --config-file=../pyproject.toml .
|
||||||
'';
|
'';
|
||||||
|
DJANGO_SETTINGS_MODULE = "network_inventory.settings.ram_test";
|
||||||
};
|
};
|
||||||
tests = pkgs.stdenv.mkDerivation {
|
tests = pkgs.stdenv.mkDerivation {
|
||||||
dontPatch = true;
|
dontPatch = true;
|
||||||
|
|
|
@ -20,14 +20,14 @@ tests = ["mypy (>=0.800)", "pytest", "pytest-asyncio"]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "astroid"
|
name = "astroid"
|
||||||
version = "2.15.5"
|
version = "2.15.6"
|
||||||
description = "An abstract syntax tree for Python with inference support."
|
description = "An abstract syntax tree for Python with inference support."
|
||||||
category = "dev"
|
category = "dev"
|
||||||
optional = false
|
optional = false
|
||||||
python-versions = ">=3.7.2"
|
python-versions = ">=3.7.2"
|
||||||
files = [
|
files = [
|
||||||
{file = "astroid-2.15.5-py3-none-any.whl", hash = "sha256:078e5212f9885fa85fbb0cf0101978a336190aadea6e13305409d099f71b2324"},
|
{file = "astroid-2.15.6-py3-none-any.whl", hash = "sha256:389656ca57b6108f939cf5d2f9a2a825a3be50ba9d589670f393236e0a03b91c"},
|
||||||
{file = "astroid-2.15.5.tar.gz", hash = "sha256:1039262575027b441137ab4a62a793a9b43defb42c32d5670f38686207cd780f"},
|
{file = "astroid-2.15.6.tar.gz", hash = "sha256:903f024859b7c7687d7a7f3a3f73b17301f8e42dfd9cc9df9d4418172d3e2dbd"},
|
||||||
]
|
]
|
||||||
|
|
||||||
[package.dependencies]
|
[package.dependencies]
|
||||||
|
@ -38,22 +38,6 @@ wrapt = [
|
||||||
{version = ">=1.14,<2", markers = "python_version >= \"3.11\""},
|
{version = ">=1.14,<2", markers = "python_version >= \"3.11\""},
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
|
||||||
name = "autopep8"
|
|
||||||
version = "2.0.2"
|
|
||||||
description = "A tool that automatically formats Python code to conform to the PEP 8 style guide"
|
|
||||||
category = "dev"
|
|
||||||
optional = false
|
|
||||||
python-versions = ">=3.6"
|
|
||||||
files = [
|
|
||||||
{file = "autopep8-2.0.2-py2.py3-none-any.whl", hash = "sha256:86e9303b5e5c8160872b2f5ef611161b2893e9bfe8ccc7e2f76385947d57a2f1"},
|
|
||||||
{file = "autopep8-2.0.2.tar.gz", hash = "sha256:f9849cdd62108cb739dbcdbfb7fdcc9a30d1b63c4cc3e1c1f893b5360941b61c"},
|
|
||||||
]
|
|
||||||
|
|
||||||
[package.dependencies]
|
|
||||||
pycodestyle = ">=2.10.0"
|
|
||||||
tomli = {version = "*", markers = "python_version < \"3.11\""}
|
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "black"
|
name = "black"
|
||||||
version = "22.12.0"
|
version = "22.12.0"
|
||||||
|
@ -92,14 +76,14 @@ uvloop = ["uvloop (>=0.15.2)"]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "click"
|
name = "click"
|
||||||
version = "8.1.3"
|
version = "8.1.4"
|
||||||
description = "Composable command line interface toolkit"
|
description = "Composable command line interface toolkit"
|
||||||
category = "dev"
|
category = "dev"
|
||||||
optional = false
|
optional = false
|
||||||
python-versions = ">=3.7"
|
python-versions = ">=3.7"
|
||||||
files = [
|
files = [
|
||||||
{file = "click-8.1.3-py3-none-any.whl", hash = "sha256:bb4d8133cb15a609f44e8213d9b391b0809795062913b383c62be0ee95b1db48"},
|
{file = "click-8.1.4-py3-none-any.whl", hash = "sha256:2739815aaa5d2c986a88f1e9230c55e17f0caad3d958a5e13ad0797c166db9e3"},
|
||||||
{file = "click-8.1.3.tar.gz", hash = "sha256:7682dc8afb30297001674575ea00d1814d808d6a36af415a82bd481d37ba7b8e"},
|
{file = "click-8.1.4.tar.gz", hash = "sha256:b97d0c74955da062a7d4ef92fadb583806a585b2ea81958a81bd72726cbb8e37"},
|
||||||
]
|
]
|
||||||
|
|
||||||
[package.dependencies]
|
[package.dependencies]
|
||||||
|
@ -200,14 +184,14 @@ graph = ["objgraph (>=1.7.2)"]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "django"
|
name = "django"
|
||||||
version = "4.2.2"
|
version = "4.2.3"
|
||||||
description = "A high-level Python web framework that encourages rapid development and clean, pragmatic design."
|
description = "A high-level Python web framework that encourages rapid development and clean, pragmatic design."
|
||||||
category = "main"
|
category = "main"
|
||||||
optional = false
|
optional = false
|
||||||
python-versions = ">=3.8"
|
python-versions = ">=3.8"
|
||||||
files = [
|
files = [
|
||||||
{file = "Django-4.2.2-py3-none-any.whl", hash = "sha256:672b3fa81e1f853bb58be1b51754108ab4ffa12a77c06db86aa8df9ed0c46fe5"},
|
{file = "Django-4.2.3-py3-none-any.whl", hash = "sha256:f7c7852a5ac5a3da5a8d5b35cc6168f31b605971441798dac845f17ca8028039"},
|
||||||
{file = "Django-4.2.2.tar.gz", hash = "sha256:2a6b6fbff5b59dd07bef10bcb019bee2ea97a30b2a656d51346596724324badf"},
|
{file = "Django-4.2.3.tar.gz", hash = "sha256:45a747e1c5b3d6df1b141b1481e193b033fd1fdbda3ff52677dc81afdaacbaed"},
|
||||||
]
|
]
|
||||||
|
|
||||||
[package.dependencies]
|
[package.dependencies]
|
||||||
|
@ -275,14 +259,14 @@ Django = ">=2.2"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "django-htmx"
|
name = "django-htmx"
|
||||||
version = "1.15.0"
|
version = "1.16.0"
|
||||||
description = "Extensions for using Django with htmx."
|
description = "Extensions for using Django with htmx."
|
||||||
category = "main"
|
category = "main"
|
||||||
optional = false
|
optional = false
|
||||||
python-versions = ">=3.7"
|
python-versions = ">=3.8"
|
||||||
files = [
|
files = [
|
||||||
{file = "django_htmx-1.15.0-py3-none-any.whl", hash = "sha256:b76068485905ad9f911419746f07f877633bb036c0870a0f9fc13dec42c6e425"},
|
{file = "django_htmx-1.16.0-py3-none-any.whl", hash = "sha256:360d11266666e5d92bda57069f671f2c04642eb1fc071e4c4160cf9f504cbfa6"},
|
||||||
{file = "django_htmx-1.15.0.tar.gz", hash = "sha256:bac7ff59bf507db6d40424f635f83889ce028a54f47663f227083413de22cabf"},
|
{file = "django_htmx-1.16.0.tar.gz", hash = "sha256:56a65045e079503877ba1354acb481030cf54da1e1f731d33c280e0a14b214cf"},
|
||||||
]
|
]
|
||||||
|
|
||||||
[package.dependencies]
|
[package.dependencies]
|
||||||
|
@ -322,16 +306,56 @@ python-monkey-business = ">=1.0.0"
|
||||||
dev = ["Pillow", "black", "dj-database-url", "django-selenosis", "flake8", "pytest", "pytest-cov", "pytest-django", "pytest-xdist", "selenium"]
|
dev = ["Pillow", "black", "dj-database-url", "django-selenosis", "flake8", "pytest", "pytest-cov", "pytest-django", "pytest-xdist", "selenium"]
|
||||||
test = ["Pillow", "dj-database-url", "django-selenosis", "pytest", "pytest-cov", "pytest-django", "pytest-xdist", "selenium"]
|
test = ["Pillow", "dj-database-url", "django-selenosis", "pytest", "pytest-cov", "pytest-django", "pytest-xdist", "selenium"]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "django-stubs"
|
||||||
|
version = "4.2.3"
|
||||||
|
description = "Mypy stubs for Django"
|
||||||
|
category = "dev"
|
||||||
|
optional = false
|
||||||
|
python-versions = ">=3.8"
|
||||||
|
files = [
|
||||||
|
{file = "django-stubs-4.2.3.tar.gz", hash = "sha256:dadab39b46d9ae8f37a8e879c590f39a9e042b565c03fa0c5a8f754b441b1f23"},
|
||||||
|
{file = "django_stubs-4.2.3-py3-none-any.whl", hash = "sha256:e30e2e4927ba14bec587ed2c686404b6b8e473cabe9baca445e7d2e1e0d7b14f"},
|
||||||
|
]
|
||||||
|
|
||||||
|
[package.dependencies]
|
||||||
|
django = "*"
|
||||||
|
django-stubs-ext = ">=4.2.2"
|
||||||
|
mypy = ">=1.0.0"
|
||||||
|
tomli = {version = "*", markers = "python_version < \"3.11\""}
|
||||||
|
types-pytz = "*"
|
||||||
|
types-PyYAML = "*"
|
||||||
|
typing-extensions = "*"
|
||||||
|
|
||||||
|
[package.extras]
|
||||||
|
compatible-mypy = ["mypy (>=1.4.0,<1.5.0)"]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "django-stubs-ext"
|
||||||
|
version = "4.2.2"
|
||||||
|
description = "Monkey-patching and extensions for django-stubs"
|
||||||
|
category = "dev"
|
||||||
|
optional = false
|
||||||
|
python-versions = ">=3.8"
|
||||||
|
files = [
|
||||||
|
{file = "django-stubs-ext-4.2.2.tar.gz", hash = "sha256:c69d1cc46f1c4c3b7894b685a5022c29b2a36c7cfb52e23762eaf357ebfc2c98"},
|
||||||
|
{file = "django_stubs_ext-4.2.2-py3-none-any.whl", hash = "sha256:fdacc65a14d2d4b97334b58ff178a5853ec8c8c76cec406e417916ad67536ce4"},
|
||||||
|
]
|
||||||
|
|
||||||
|
[package.dependencies]
|
||||||
|
django = "*"
|
||||||
|
typing-extensions = "*"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "django-tables2"
|
name = "django-tables2"
|
||||||
version = "2.5.3"
|
version = "2.6.0"
|
||||||
description = "Table/data-grid framework for Django"
|
description = "Table/data-grid framework for Django"
|
||||||
category = "main"
|
category = "main"
|
||||||
optional = false
|
optional = false
|
||||||
python-versions = "*"
|
python-versions = "*"
|
||||||
files = [
|
files = [
|
||||||
{file = "django-tables2-2.5.3.tar.gz", hash = "sha256:f6c1623aac188d29aae9cf6b4de3211c96c525e49890654bec3359c181600eb9"},
|
{file = "django-tables2-2.6.0.tar.gz", hash = "sha256:479eed04007cc04bcf764a6fb7a5e3955d94b878ba7f3a4bd4edbd2f7769e08d"},
|
||||||
{file = "django_tables2-2.5.3-py2.py3-none-any.whl", hash = "sha256:e336fdf8899a8fab110550a40cad956064bd4054818e0b972c1893b3e2542168"},
|
{file = "django_tables2-2.6.0-py2.py3-none-any.whl", hash = "sha256:04f23c1181d93716c67085a3c324b449180fd0c5162ef4619acb0b2d9a166133"},
|
||||||
]
|
]
|
||||||
|
|
||||||
[package.dependencies]
|
[package.dependencies]
|
||||||
|
@ -354,14 +378,14 @@ files = [
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "exceptiongroup"
|
name = "exceptiongroup"
|
||||||
version = "1.1.1"
|
version = "1.1.2"
|
||||||
description = "Backport of PEP 654 (exception groups)"
|
description = "Backport of PEP 654 (exception groups)"
|
||||||
category = "dev"
|
category = "dev"
|
||||||
optional = false
|
optional = false
|
||||||
python-versions = ">=3.7"
|
python-versions = ">=3.7"
|
||||||
files = [
|
files = [
|
||||||
{file = "exceptiongroup-1.1.1-py3-none-any.whl", hash = "sha256:232c37c63e4f682982c8b6459f33a8981039e5fb8756b2074364e5055c498c9e"},
|
{file = "exceptiongroup-1.1.2-py3-none-any.whl", hash = "sha256:e346e69d186172ca7cf029c8c1d16235aa0e04035e5750b4b95039e65204328f"},
|
||||||
{file = "exceptiongroup-1.1.1.tar.gz", hash = "sha256:d484c3090ba2889ae2928419117447a14daf3c1231d5e30d0aae34f354f01785"},
|
{file = "exceptiongroup-1.1.2.tar.gz", hash = "sha256:12c3e887d6485d16943a309616de20ae5582633e0a2eda17f4e10fd61c1e8af5"},
|
||||||
]
|
]
|
||||||
|
|
||||||
[package.extras]
|
[package.extras]
|
||||||
|
@ -397,23 +421,6 @@ files = [
|
||||||
[package.dependencies]
|
[package.dependencies]
|
||||||
python-dateutil = ">=2.4"
|
python-dateutil = ">=2.4"
|
||||||
|
|
||||||
[[package]]
|
|
||||||
name = "flake8"
|
|
||||||
version = "6.0.0"
|
|
||||||
description = "the modular source code checker: pep8 pyflakes and co"
|
|
||||||
category = "dev"
|
|
||||||
optional = false
|
|
||||||
python-versions = ">=3.8.1"
|
|
||||||
files = [
|
|
||||||
{file = "flake8-6.0.0-py2.py3-none-any.whl", hash = "sha256:3833794e27ff64ea4e9cf5d410082a8b97ff1a06c16aa3d2027339cd0f1195c7"},
|
|
||||||
{file = "flake8-6.0.0.tar.gz", hash = "sha256:c61007e76655af75e6785a931f452915b371dc48f56efd765247c8fe68f2b181"},
|
|
||||||
]
|
|
||||||
|
|
||||||
[package.dependencies]
|
|
||||||
mccabe = ">=0.7.0,<0.8.0"
|
|
||||||
pycodestyle = ">=2.10.0,<2.11.0"
|
|
||||||
pyflakes = ">=3.0.0,<3.1.0"
|
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "gunicorn"
|
name = "gunicorn"
|
||||||
version = "20.1.0"
|
version = "20.1.0"
|
||||||
|
@ -561,6 +568,53 @@ Faker = ">=5.4.0,<12.1"
|
||||||
[package.extras]
|
[package.extras]
|
||||||
tests = ["Django (>=3.0)", "Flask (>=1.0)", "Marshmallow (>=3.9)", "SQLAlchemy (>=1.1.4)", "flask-sqlalchemy (>=2.1)", "mongoengine (>=0.10.1)", "peewee (>=3.7.0)", "pony (>=0.7)", "psycopg2-binary (>=2.8.4)", "pytest"]
|
tests = ["Django (>=3.0)", "Flask (>=1.0)", "Marshmallow (>=3.9)", "SQLAlchemy (>=1.1.4)", "flask-sqlalchemy (>=2.1)", "mongoengine (>=0.10.1)", "peewee (>=3.7.0)", "pony (>=0.7)", "psycopg2-binary (>=2.8.4)", "pytest"]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "mypy"
|
||||||
|
version = "1.4.1"
|
||||||
|
description = "Optional static typing for Python"
|
||||||
|
category = "dev"
|
||||||
|
optional = false
|
||||||
|
python-versions = ">=3.7"
|
||||||
|
files = [
|
||||||
|
{file = "mypy-1.4.1-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:566e72b0cd6598503e48ea610e0052d1b8168e60a46e0bfd34b3acf2d57f96a8"},
|
||||||
|
{file = "mypy-1.4.1-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:ca637024ca67ab24a7fd6f65d280572c3794665eaf5edcc7e90a866544076878"},
|
||||||
|
{file = "mypy-1.4.1-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:0dde1d180cd84f0624c5dcaaa89c89775550a675aff96b5848de78fb11adabcd"},
|
||||||
|
{file = "mypy-1.4.1-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:8c4d8e89aa7de683e2056a581ce63c46a0c41e31bd2b6d34144e2c80f5ea53dc"},
|
||||||
|
{file = "mypy-1.4.1-cp310-cp310-win_amd64.whl", hash = "sha256:bfdca17c36ae01a21274a3c387a63aa1aafe72bff976522886869ef131b937f1"},
|
||||||
|
{file = "mypy-1.4.1-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:7549fbf655e5825d787bbc9ecf6028731973f78088fbca3a1f4145c39ef09462"},
|
||||||
|
{file = "mypy-1.4.1-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:98324ec3ecf12296e6422939e54763faedbfcc502ea4a4c38502082711867258"},
|
||||||
|
{file = "mypy-1.4.1-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:141dedfdbfe8a04142881ff30ce6e6653c9685b354876b12e4fe6c78598b45e2"},
|
||||||
|
{file = "mypy-1.4.1-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:8207b7105829eca6f3d774f64a904190bb2231de91b8b186d21ffd98005f14a7"},
|
||||||
|
{file = "mypy-1.4.1-cp311-cp311-win_amd64.whl", hash = "sha256:16f0db5b641ba159eff72cff08edc3875f2b62b2fa2bc24f68c1e7a4e8232d01"},
|
||||||
|
{file = "mypy-1.4.1-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:470c969bb3f9a9efcedbadcd19a74ffb34a25f8e6b0e02dae7c0e71f8372f97b"},
|
||||||
|
{file = "mypy-1.4.1-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:e5952d2d18b79f7dc25e62e014fe5a23eb1a3d2bc66318df8988a01b1a037c5b"},
|
||||||
|
{file = "mypy-1.4.1-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:190b6bab0302cec4e9e6767d3eb66085aef2a1cc98fe04936d8a42ed2ba77bb7"},
|
||||||
|
{file = "mypy-1.4.1-cp37-cp37m-win_amd64.whl", hash = "sha256:9d40652cc4fe33871ad3338581dca3297ff5f2213d0df345bcfbde5162abf0c9"},
|
||||||
|
{file = "mypy-1.4.1-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:01fd2e9f85622d981fd9063bfaef1aed6e336eaacca00892cd2d82801ab7c042"},
|
||||||
|
{file = "mypy-1.4.1-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:2460a58faeea905aeb1b9b36f5065f2dc9a9c6e4c992a6499a2360c6c74ceca3"},
|
||||||
|
{file = "mypy-1.4.1-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:a2746d69a8196698146a3dbe29104f9eb6a2a4d8a27878d92169a6c0b74435b6"},
|
||||||
|
{file = "mypy-1.4.1-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:ae704dcfaa180ff7c4cfbad23e74321a2b774f92ca77fd94ce1049175a21c97f"},
|
||||||
|
{file = "mypy-1.4.1-cp38-cp38-win_amd64.whl", hash = "sha256:43d24f6437925ce50139a310a64b2ab048cb2d3694c84c71c3f2a1626d8101dc"},
|
||||||
|
{file = "mypy-1.4.1-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:c482e1246726616088532b5e964e39765b6d1520791348e6c9dc3af25b233828"},
|
||||||
|
{file = "mypy-1.4.1-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:43b592511672017f5b1a483527fd2684347fdffc041c9ef53428c8dc530f79a3"},
|
||||||
|
{file = "mypy-1.4.1-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:34a9239d5b3502c17f07fd7c0b2ae6b7dd7d7f6af35fbb5072c6208e76295816"},
|
||||||
|
{file = "mypy-1.4.1-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:5703097c4936bbb9e9bce41478c8d08edd2865e177dc4c52be759f81ee4dd26c"},
|
||||||
|
{file = "mypy-1.4.1-cp39-cp39-win_amd64.whl", hash = "sha256:e02d700ec8d9b1859790c0475df4e4092c7bf3272a4fd2c9f33d87fac4427b8f"},
|
||||||
|
{file = "mypy-1.4.1-py3-none-any.whl", hash = "sha256:45d32cec14e7b97af848bddd97d85ea4f0db4d5a149ed9676caa4eb2f7402bb4"},
|
||||||
|
{file = "mypy-1.4.1.tar.gz", hash = "sha256:9bbcd9ab8ea1f2e1c8031c21445b511442cc45c89951e49bbf852cbb70755b1b"},
|
||||||
|
]
|
||||||
|
|
||||||
|
[package.dependencies]
|
||||||
|
mypy-extensions = ">=1.0.0"
|
||||||
|
tomli = {version = ">=1.1.0", markers = "python_version < \"3.11\""}
|
||||||
|
typing-extensions = ">=4.1.0"
|
||||||
|
|
||||||
|
[package.extras]
|
||||||
|
dmypy = ["psutil (>=4.0)"]
|
||||||
|
install-types = ["pip"]
|
||||||
|
python2 = ["typed-ast (>=1.4.0,<2)"]
|
||||||
|
reports = ["lxml"]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "mypy-extensions"
|
name = "mypy-extensions"
|
||||||
version = "1.0.0"
|
version = "1.0.0"
|
||||||
|
@ -613,28 +667,16 @@ files = [
|
||||||
{file = "pathspec-0.11.1.tar.gz", hash = "sha256:2798de800fa92780e33acca925945e9a19a133b715067cf165b8866c15a31687"},
|
{file = "pathspec-0.11.1.tar.gz", hash = "sha256:2798de800fa92780e33acca925945e9a19a133b715067cf165b8866c15a31687"},
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
|
||||||
name = "pep8"
|
|
||||||
version = "1.7.1"
|
|
||||||
description = "Python style guide checker"
|
|
||||||
category = "dev"
|
|
||||||
optional = false
|
|
||||||
python-versions = "*"
|
|
||||||
files = [
|
|
||||||
{file = "pep8-1.7.1-py2.py3-none-any.whl", hash = "sha256:b22cfae5db09833bb9bd7c8463b53e1a9c9b39f12e304a8d0bba729c501827ee"},
|
|
||||||
{file = "pep8-1.7.1.tar.gz", hash = "sha256:fe249b52e20498e59e0b5c5256aa52ee99fc295b26ec9eaa85776ffdb9fe6374"},
|
|
||||||
]
|
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "platformdirs"
|
name = "platformdirs"
|
||||||
version = "3.8.0"
|
version = "3.8.1"
|
||||||
description = "A small Python package for determining appropriate platform-specific dirs, e.g. a \"user data dir\"."
|
description = "A small Python package for determining appropriate platform-specific dirs, e.g. a \"user data dir\"."
|
||||||
category = "dev"
|
category = "dev"
|
||||||
optional = false
|
optional = false
|
||||||
python-versions = ">=3.7"
|
python-versions = ">=3.7"
|
||||||
files = [
|
files = [
|
||||||
{file = "platformdirs-3.8.0-py3-none-any.whl", hash = "sha256:ca9ed98ce73076ba72e092b23d3c93ea6c4e186b3f1c3dad6edd98ff6ffcca2e"},
|
{file = "platformdirs-3.8.1-py3-none-any.whl", hash = "sha256:cec7b889196b9144d088e4c57d9ceef7374f6c39694ad1577a0aab50d27ea28c"},
|
||||||
{file = "platformdirs-3.8.0.tar.gz", hash = "sha256:b0cabcb11063d21a0b261d557acb0a9d2126350e63b70cdf7db6347baea456dc"},
|
{file = "platformdirs-3.8.1.tar.gz", hash = "sha256:f87ca4fcff7d2b0f81c6a748a77973d7af0f4d526f98f308477c3c436c74d528"},
|
||||||
]
|
]
|
||||||
|
|
||||||
[package.extras]
|
[package.extras]
|
||||||
|
@ -729,30 +771,6 @@ files = [
|
||||||
{file = "psycopg2_binary-2.9.6-cp39-cp39-win_amd64.whl", hash = "sha256:f6a88f384335bb27812293fdb11ac6aee2ca3f51d3c7820fe03de0a304ab6249"},
|
{file = "psycopg2_binary-2.9.6-cp39-cp39-win_amd64.whl", hash = "sha256:f6a88f384335bb27812293fdb11ac6aee2ca3f51d3c7820fe03de0a304ab6249"},
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
|
||||||
name = "pycodestyle"
|
|
||||||
version = "2.10.0"
|
|
||||||
description = "Python style guide checker"
|
|
||||||
category = "dev"
|
|
||||||
optional = false
|
|
||||||
python-versions = ">=3.6"
|
|
||||||
files = [
|
|
||||||
{file = "pycodestyle-2.10.0-py2.py3-none-any.whl", hash = "sha256:8a4eaf0d0495c7395bdab3589ac2db602797d76207242c17d470186815706610"},
|
|
||||||
{file = "pycodestyle-2.10.0.tar.gz", hash = "sha256:347187bdb476329d98f695c213d7295a846d1152ff4fe9bacb8a9590b8ee7053"},
|
|
||||||
]
|
|
||||||
|
|
||||||
[[package]]
|
|
||||||
name = "pyflakes"
|
|
||||||
version = "3.0.1"
|
|
||||||
description = "passive checker of Python programs"
|
|
||||||
category = "dev"
|
|
||||||
optional = false
|
|
||||||
python-versions = ">=3.6"
|
|
||||||
files = [
|
|
||||||
{file = "pyflakes-3.0.1-py2.py3-none-any.whl", hash = "sha256:ec55bf7fe21fff7f1ad2f7da62363d749e2a470500eab1b555334b67aa1ef8cf"},
|
|
||||||
{file = "pyflakes-3.0.1.tar.gz", hash = "sha256:ec8b276a6b60bd80defed25add7e439881c19e64850afd9b346283d4165fd0fd"},
|
|
||||||
]
|
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "pylint"
|
name = "pylint"
|
||||||
version = "2.17.4"
|
version = "2.17.4"
|
||||||
|
@ -783,6 +801,41 @@ typing-extensions = {version = ">=3.10.0", markers = "python_version < \"3.10\""
|
||||||
spelling = ["pyenchant (>=3.2,<4.0)"]
|
spelling = ["pyenchant (>=3.2,<4.0)"]
|
||||||
testutils = ["gitpython (>3)"]
|
testutils = ["gitpython (>3)"]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "pylint-django"
|
||||||
|
version = "2.5.3"
|
||||||
|
description = "A Pylint plugin to help Pylint understand the Django web framework"
|
||||||
|
category = "dev"
|
||||||
|
optional = false
|
||||||
|
python-versions = "*"
|
||||||
|
files = [
|
||||||
|
{file = "pylint-django-2.5.3.tar.gz", hash = "sha256:0ac090d106c62fe33782a1d01bda1610b761bb1c9bf5035ced9d5f23a13d8591"},
|
||||||
|
{file = "pylint_django-2.5.3-py3-none-any.whl", hash = "sha256:56b12b6adf56d548412445bd35483034394a1a94901c3f8571980a13882299d5"},
|
||||||
|
]
|
||||||
|
|
||||||
|
[package.dependencies]
|
||||||
|
pylint = ">=2.0,<3"
|
||||||
|
pylint-plugin-utils = ">=0.7"
|
||||||
|
|
||||||
|
[package.extras]
|
||||||
|
for-tests = ["coverage", "django-tables2", "django-tastypie", "factory-boy", "pylint (>=2.13)", "pytest", "wheel"]
|
||||||
|
with-django = ["Django"]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "pylint-plugin-utils"
|
||||||
|
version = "0.8.2"
|
||||||
|
description = "Utilities and helpers for writing Pylint plugins"
|
||||||
|
category = "dev"
|
||||||
|
optional = false
|
||||||
|
python-versions = ">=3.7,<4.0"
|
||||||
|
files = [
|
||||||
|
{file = "pylint_plugin_utils-0.8.2-py3-none-any.whl", hash = "sha256:ae11664737aa2effbf26f973a9e0b6779ab7106ec0adc5fe104b0907ca04e507"},
|
||||||
|
{file = "pylint_plugin_utils-0.8.2.tar.gz", hash = "sha256:d3cebf68a38ba3fba23a873809155562571386d4c1b03e5b4c4cc26c3eee93e4"},
|
||||||
|
]
|
||||||
|
|
||||||
|
[package.dependencies]
|
||||||
|
pylint = ">=1.7"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "pytest"
|
name = "pytest"
|
||||||
version = "7.4.0"
|
version = "7.4.0"
|
||||||
|
@ -900,14 +953,14 @@ test = ["coverage", "pycodestyle", "pyflakes", "pylint", "pytest", "pytest-cov"]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "python-lsp-server"
|
name = "python-lsp-server"
|
||||||
version = "1.7.3"
|
version = "1.7.4"
|
||||||
description = "Python Language Server for the Language Server Protocol"
|
description = "Python Language Server for the Language Server Protocol"
|
||||||
category = "dev"
|
category = "dev"
|
||||||
optional = false
|
optional = false
|
||||||
python-versions = ">=3.7"
|
python-versions = ">=3.7"
|
||||||
files = [
|
files = [
|
||||||
{file = "python-lsp-server-1.7.3.tar.gz", hash = "sha256:a31b0525be6ec831c7d2b476b744e5aa5074633e1d1b77ee97f332cde15983ea"},
|
{file = "python-lsp-server-1.7.4.tar.gz", hash = "sha256:c84254485a4d9431b24ecefd59741d21c00165611bcf6037bd7d54d0ed06a197"},
|
||||||
{file = "python_lsp_server-1.7.3-py3-none-any.whl", hash = "sha256:f4ae64834da1d4312067a8ee05a76c7652167c3c90d1cef44022366d695c4c0e"},
|
{file = "python_lsp_server-1.7.4-py3-none-any.whl", hash = "sha256:f8053f7aefcb60af4e91f3fab1a093b15ba0c4688ba67e6ab69e7b73e997b2cb"},
|
||||||
]
|
]
|
||||||
|
|
||||||
[package.dependencies]
|
[package.dependencies]
|
||||||
|
@ -947,29 +1000,6 @@ files = [
|
||||||
[package.dependencies]
|
[package.dependencies]
|
||||||
six = ">=1.7.0"
|
six = ">=1.7.0"
|
||||||
|
|
||||||
[[package]]
|
|
||||||
name = "pytoolconfig"
|
|
||||||
version = "1.2.5"
|
|
||||||
description = "Python tool configuration"
|
|
||||||
category = "dev"
|
|
||||||
optional = false
|
|
||||||
python-versions = ">=3.7"
|
|
||||||
files = [
|
|
||||||
{file = "pytoolconfig-1.2.5-py3-none-any.whl", hash = "sha256:239ba9d3e537b91d0243275a497700ea39a5e259ddb80421c366e3b288bf30fe"},
|
|
||||||
{file = "pytoolconfig-1.2.5.tar.gz", hash = "sha256:a50f9dfe23b03a9d40414c1fdf902fefbeae12f2ac75a3c8f915944d6ffac279"},
|
|
||||||
]
|
|
||||||
|
|
||||||
[package.dependencies]
|
|
||||||
packaging = ">=22.0"
|
|
||||||
platformdirs = {version = ">=1.4.4", optional = true, markers = "extra == \"global\""}
|
|
||||||
tomli = {version = ">=2.0.1", markers = "python_version < \"3.11\""}
|
|
||||||
|
|
||||||
[package.extras]
|
|
||||||
doc = ["sphinx (>=4.5.0)", "tabulate (>=0.8.9)"]
|
|
||||||
gendocs = ["pytoolconfig[doc]", "sphinx (>=4.5.0)", "sphinx-autodoc-typehints (>=1.18.1)", "sphinx-rtd-theme (>=1.0.0)"]
|
|
||||||
global = ["platformdirs (>=1.4.4)"]
|
|
||||||
validation = ["pydantic (>=1.7.4)"]
|
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "pyyaml"
|
name = "pyyaml"
|
||||||
version = "6.0"
|
version = "6.0"
|
||||||
|
@ -1020,25 +1050,6 @@ files = [
|
||||||
{file = "PyYAML-6.0.tar.gz", hash = "sha256:68fb519c14306fec9720a2a5b45bc9f0c8d1b9c72adf45c37baedfcd949c35a2"},
|
{file = "PyYAML-6.0.tar.gz", hash = "sha256:68fb519c14306fec9720a2a5b45bc9f0c8d1b9c72adf45c37baedfcd949c35a2"},
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
|
||||||
name = "rope"
|
|
||||||
version = "1.8.0"
|
|
||||||
description = "a python refactoring library..."
|
|
||||||
category = "dev"
|
|
||||||
optional = false
|
|
||||||
python-versions = ">=3.7"
|
|
||||||
files = [
|
|
||||||
{file = "rope-1.8.0-py3-none-any.whl", hash = "sha256:0767424ed40ce237dcf1c1f5088054fef960e5b19f4a0850783a259a3600d7bd"},
|
|
||||||
{file = "rope-1.8.0.tar.gz", hash = "sha256:3de1d1f1cf2412540c6a150067fe25298175e7c2b72455b6ca8395f61678da82"},
|
|
||||||
]
|
|
||||||
|
|
||||||
[package.dependencies]
|
|
||||||
pytoolconfig = {version = ">=1.2.2", extras = ["global"]}
|
|
||||||
|
|
||||||
[package.extras]
|
|
||||||
dev = ["build (>=0.7.0)", "pip-tools (>=6.12.1)", "pre-commit (>=2.20.0)", "pytest (>=7.0.1)", "pytest-timeout (>=2.1.0)", "toml (>=0.10.2)"]
|
|
||||||
doc = ["pytoolconfig[doc]", "sphinx (>=4.5.0)", "sphinx-autodoc-typehints (>=1.18.1)", "sphinx-rtd-theme (>=1.0.0)"]
|
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "setuptools"
|
name = "setuptools"
|
||||||
version = "68.0.0"
|
version = "68.0.0"
|
||||||
|
@ -1109,16 +1120,40 @@ files = [
|
||||||
{file = "tomlkit-0.11.8.tar.gz", hash = "sha256:9330fc7faa1db67b541b28e62018c17d20be733177d290a13b24c62d1614e0c3"},
|
{file = "tomlkit-0.11.8.tar.gz", hash = "sha256:9330fc7faa1db67b541b28e62018c17d20be733177d290a13b24c62d1614e0c3"},
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "types-pytz"
|
||||||
|
version = "2023.3.0.0"
|
||||||
|
description = "Typing stubs for pytz"
|
||||||
|
category = "dev"
|
||||||
|
optional = false
|
||||||
|
python-versions = "*"
|
||||||
|
files = [
|
||||||
|
{file = "types-pytz-2023.3.0.0.tar.gz", hash = "sha256:ecdc70d543aaf3616a7e48631543a884f74205f284cefd6649ddf44c6a820aac"},
|
||||||
|
{file = "types_pytz-2023.3.0.0-py3-none-any.whl", hash = "sha256:4fc2a7fbbc315f0b6630e0b899fd6c743705abe1094d007b0e612d10da15e0f3"},
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "types-pyyaml"
|
||||||
|
version = "6.0.12.10"
|
||||||
|
description = "Typing stubs for PyYAML"
|
||||||
|
category = "dev"
|
||||||
|
optional = false
|
||||||
|
python-versions = "*"
|
||||||
|
files = [
|
||||||
|
{file = "types-PyYAML-6.0.12.10.tar.gz", hash = "sha256:ebab3d0700b946553724ae6ca636ea932c1b0868701d4af121630e78d695fc97"},
|
||||||
|
{file = "types_PyYAML-6.0.12.10-py3-none-any.whl", hash = "sha256:662fa444963eff9b68120d70cda1af5a5f2aa57900003c2006d7626450eaae5f"},
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "typing-extensions"
|
name = "typing-extensions"
|
||||||
version = "4.6.3"
|
version = "4.7.1"
|
||||||
description = "Backported and Experimental Type Hints for Python 3.7+"
|
description = "Backported and Experimental Type Hints for Python 3.7+"
|
||||||
category = "main"
|
category = "main"
|
||||||
optional = false
|
optional = false
|
||||||
python-versions = ">=3.7"
|
python-versions = ">=3.7"
|
||||||
files = [
|
files = [
|
||||||
{file = "typing_extensions-4.6.3-py3-none-any.whl", hash = "sha256:88a4153d8505aabbb4e13aacb7c486c2b4a33ca3b3f807914a9b4c844c471c26"},
|
{file = "typing_extensions-4.7.1-py3-none-any.whl", hash = "sha256:440d5dd3af93b060174bf433bccd69b0babc3b15b1a8dca43789fd7f61514b36"},
|
||||||
{file = "typing_extensions-4.6.3.tar.gz", hash = "sha256:d91d5919357fe7f681a9f2b5b4cb2a5f1ef0a1e9f59c4d8ff0d3491e05c0ffd5"},
|
{file = "typing_extensions-4.7.1.tar.gz", hash = "sha256:b75ddc264f0ba5615db7ba217daeb99701ad295353c45f9e95963337ceeeffb2"},
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
|
@ -1289,19 +1324,7 @@ files = [
|
||||||
{file = "wrapt-1.15.0.tar.gz", hash = "sha256:d06730c6aed78cee4126234cf2d071e01b44b915e725a6cb439a879ec9754a3a"},
|
{file = "wrapt-1.15.0.tar.gz", hash = "sha256:d06730c6aed78cee4126234cf2d071e01b44b915e725a6cb439a879ec9754a3a"},
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
|
||||||
name = "yapf"
|
|
||||||
version = "0.32.0"
|
|
||||||
description = "A formatter for Python code."
|
|
||||||
category = "dev"
|
|
||||||
optional = false
|
|
||||||
python-versions = "*"
|
|
||||||
files = [
|
|
||||||
{file = "yapf-0.32.0-py2.py3-none-any.whl", hash = "sha256:8fea849025584e486fd06d6ba2bed717f396080fd3cc236ba10cb97c4c51cf32"},
|
|
||||||
{file = "yapf-0.32.0.tar.gz", hash = "sha256:a3f5085d37ef7e3e004c4ba9f9b3e40c54ff1901cd111f05145ae313a7c67d1b"},
|
|
||||||
]
|
|
||||||
|
|
||||||
[metadata]
|
[metadata]
|
||||||
lock-version = "2.0"
|
lock-version = "2.0"
|
||||||
python-versions = "^3.9"
|
python-versions = "^3.9"
|
||||||
content-hash = "95419a1919aadc2d6bbd680b89480fa6b53f4dc29d2f7e2ea7ec7f849bfba1ba"
|
content-hash = "56454bd1da936edf92442e1f87d0cdb1ace8cda9297e33f4eba8a98230cc4610"
|
||||||
|
|
|
@ -1,5 +1,8 @@
|
||||||
[tool.black]
|
[tool.pylint]
|
||||||
line-length = 79
|
max-line-length = 88
|
||||||
|
load-plugins = [
|
||||||
|
"pylint_django",
|
||||||
|
]
|
||||||
|
|
||||||
[tool.poetry]
|
[tool.poetry]
|
||||||
name = "network_inventory"
|
name = "network_inventory"
|
||||||
|
@ -11,6 +14,45 @@ packages = [
|
||||||
{ include = "src" },
|
{ include = "src" },
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[tool.mypy]
|
||||||
|
exclude = [
|
||||||
|
"tests/",
|
||||||
|
]
|
||||||
|
plugins = ["mypy_django_plugin.main"]
|
||||||
|
mypy_path = "./src"
|
||||||
|
# Start off with these
|
||||||
|
warn_unused_configs = true
|
||||||
|
warn_redundant_casts = true
|
||||||
|
warn_unused_ignores = true
|
||||||
|
|
||||||
|
# Getting these passing should be easy
|
||||||
|
strict_equality = true
|
||||||
|
strict_concatenate = true
|
||||||
|
|
||||||
|
# Strongly recommend enabling this one as soon as you can
|
||||||
|
#check_untyped_defs = true
|
||||||
|
|
||||||
|
# These shouldn't be too much additional work, but may be tricky to
|
||||||
|
# get passing if you use a lot of untyped libraries
|
||||||
|
#disallow_subclassing_any = true
|
||||||
|
#disallow_untyped_decorators = true
|
||||||
|
#disallow_any_generics = true
|
||||||
|
|
||||||
|
[tool.django-stubs]
|
||||||
|
django_settings_module = "network_inventory.settings.local"
|
||||||
|
|
||||||
|
[[tool.mypy.overrides]]
|
||||||
|
module = [
|
||||||
|
"nested_admin.*",
|
||||||
|
"django_tables2.*",
|
||||||
|
"floppyforms.*",
|
||||||
|
"django_filters.*",
|
||||||
|
"crispy_forms.*",
|
||||||
|
"mixer.*",
|
||||||
|
"guardian.*",
|
||||||
|
]
|
||||||
|
ignore_missing_imports = true
|
||||||
|
|
||||||
[tool.poetry.group.main.dependencies]
|
[tool.poetry.group.main.dependencies]
|
||||||
python = "^3.9"
|
python = "^3.9"
|
||||||
Django = "^4.1.3"
|
Django = "^4.1.3"
|
||||||
|
@ -27,21 +69,19 @@ psycopg2-binary = "^2.9.5"
|
||||||
PyYAML = "^6.0"
|
PyYAML = "^6.0"
|
||||||
|
|
||||||
[tool.poetry.group.dev.dependencies]
|
[tool.poetry.group.dev.dependencies]
|
||||||
autopep8 = "^2.0.0"
|
|
||||||
black = "^22.10.0"
|
black = "^22.10.0"
|
||||||
coverage = "^6.5.0"
|
coverage = "^6.5.0"
|
||||||
flake8 = "^6.0.0"
|
|
||||||
jedi = "^0.18.2"
|
|
||||||
mixer = "^7.2.2"
|
mixer = "^7.2.2"
|
||||||
pep8 = "^1.7.1"
|
|
||||||
pylint = "^2.15.8"
|
pylint = "^2.15.8"
|
||||||
pytest = "^7.2.0"
|
pytest = "^7.2.0"
|
||||||
pytest-cov = "^4.0.0"
|
pytest-cov = "^4.0.0"
|
||||||
pytest-django = "^4.5.2"
|
pytest-django = "^4.5.2"
|
||||||
pytest-xdist = "^3.1.0"
|
pytest-xdist = "^3.1.0"
|
||||||
rope = "^1.5.1"
|
|
||||||
yapf = "^0.32.0"
|
|
||||||
python-lsp-server = "^1.7.3"
|
python-lsp-server = "^1.7.3"
|
||||||
|
mypy = "^1.4.1"
|
||||||
|
django-stubs = "^4.2.3"
|
||||||
|
pylint-django = "^2.5.3"
|
||||||
|
execnet = "~1.9.0"
|
||||||
|
|
||||||
[build-system]
|
[build-system]
|
||||||
requires = ["poetry-core>=1.0.0"]
|
requires = ["poetry-core>=1.0.0"]
|
||||||
|
|
|
@ -11,8 +11,6 @@ def backup_view_permission(old_fuction):
|
||||||
if user.has_perm("customers.view_customer", backup.computer.customer):
|
if user.has_perm("customers.view_customer", backup.computer.customer):
|
||||||
return old_fuction(request, pk)
|
return old_fuction(request, pk)
|
||||||
else:
|
else:
|
||||||
return HttpResponseForbidden(
|
return HttpResponseForbidden("You're not allowed to access this device.")
|
||||||
"You're not allowed to access this device."
|
|
||||||
)
|
|
||||||
|
|
||||||
return new_function
|
return new_function
|
||||||
|
|
|
@ -20,18 +20,12 @@ class Backup(models.Model):
|
||||||
computer = models.ForeignKey(
|
computer = models.ForeignKey(
|
||||||
Computer, related_name="source_computer", on_delete=models.CASCADE
|
Computer, related_name="source_computer", on_delete=models.CASCADE
|
||||||
)
|
)
|
||||||
method = models.ForeignKey(
|
method = models.ForeignKey(BackupMethod, models.SET_NULL, blank=True, null=True)
|
||||||
BackupMethod, models.SET_NULL, blank=True, null=True
|
software = models.ForeignKey(Software, models.SET_NULL, blank=True, null=True)
|
||||||
)
|
|
||||||
software = models.ForeignKey(
|
|
||||||
Software, models.SET_NULL, blank=True, null=True
|
|
||||||
)
|
|
||||||
source_path = models.CharField(max_length=200, blank=True)
|
source_path = models.CharField(max_length=200, blank=True)
|
||||||
exec_time = models.TimeField(null=True, blank=True)
|
exec_time = models.TimeField(null=True, blank=True)
|
||||||
exec_days = models.ManyToManyField(Weekday, blank=True)
|
exec_days = models.ManyToManyField(Weekday, blank=True)
|
||||||
target_device = models.ManyToManyField(
|
target_device = models.ManyToManyField(Computer, through="TargetDevice", blank=True)
|
||||||
Computer, through="TargetDevice", blank=True
|
|
||||||
)
|
|
||||||
|
|
||||||
class Meta:
|
class Meta:
|
||||||
ordering = ["name"]
|
ordering = ["name"]
|
||||||
|
@ -50,9 +44,7 @@ class Backup(models.Model):
|
||||||
|
|
||||||
|
|
||||||
class TargetDevice(models.Model):
|
class TargetDevice(models.Model):
|
||||||
device = models.ForeignKey(
|
device = models.ForeignKey(Computer, models.SET_NULL, blank=True, null=True)
|
||||||
Computer, models.SET_NULL, blank=True, null=True
|
|
||||||
)
|
|
||||||
backup = models.ForeignKey(Backup, on_delete=models.CASCADE)
|
backup = models.ForeignKey(Backup, on_delete=models.CASCADE)
|
||||||
target_path = models.CharField(max_length=200, blank=True)
|
target_path = models.CharField(max_length=200, blank=True)
|
||||||
|
|
||||||
|
|
|
@ -53,9 +53,7 @@ def test_backup_detail_view_with_target_device(create_admin_user):
|
||||||
software=mixer.SELECT,
|
software=mixer.SELECT,
|
||||||
method=mixer.SELECT,
|
method=mixer.SELECT,
|
||||||
)
|
)
|
||||||
mixer.blend(
|
mixer.blend("backups.TargetDevice", device=target_computer, backup=mixer.SELECT)
|
||||||
"backups.TargetDevice", device=target_computer, backup=mixer.SELECT
|
|
||||||
)
|
|
||||||
client = Client()
|
client = Client()
|
||||||
client.login(username="pharma-admin", password="password")
|
client.login(username="pharma-admin", password="password")
|
||||||
response = client.get("/backup/" + str(backup.id) + "/")
|
response = client.get("/backup/" + str(backup.id) + "/")
|
||||||
|
@ -79,9 +77,7 @@ def test_backup_detail_view_with_notification(create_admin_user):
|
||||||
client = Client()
|
client = Client()
|
||||||
client.login(username="pharma-admin", password="password")
|
client.login(username="pharma-admin", password="password")
|
||||||
response = client.get("/backup/" + str(backup.id) + "/")
|
response = client.get("/backup/" + str(backup.id) + "/")
|
||||||
assert response.status_code == 200 and helper.in_content(
|
assert response.status_code == 200 and helper.in_content(response, notification)
|
||||||
response, notification
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def test_backup_detail_view_with_day_relation(create_admin_user):
|
def test_backup_detail_view_with_day_relation(create_admin_user):
|
||||||
|
|
|
@ -23,9 +23,7 @@ def test_customer_backup_table(create_admin_user):
|
||||||
computer = mixer.blend("computers.Computer", customer=customer)
|
computer = mixer.blend("computers.Computer", customer=customer)
|
||||||
backup = mixer.blend("backups.Backup", computer=computer)
|
backup = mixer.blend("backups.Backup", computer=computer)
|
||||||
response = client.get("/customer/" + str(customer.id) + "/backups/")
|
response = client.get("/customer/" + str(customer.id) + "/backups/")
|
||||||
assert response.status_code == 200 and helper.in_content(
|
assert response.status_code == 200 and helper.in_content(response, backup.name)
|
||||||
response, backup.name
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def test_customer_backup_table_no_backup(create_admin_user):
|
def test_customer_backup_table_no_backup(create_admin_user):
|
||||||
|
|
|
@ -3,9 +3,7 @@ from django.urls import path
|
||||||
from . import views
|
from . import views
|
||||||
|
|
||||||
urlpatterns = [
|
urlpatterns = [
|
||||||
path(
|
path("customer/<int:pk>/backups/", views.backups_table_view, name="backups"),
|
||||||
"customer/<int:pk>/backups/", views.backups_table_view, name="backups"
|
|
||||||
),
|
|
||||||
path("backup/<int:pk>/", views.backup_detail_view, name="backup"),
|
path("backup/<int:pk>/", views.backup_detail_view, name="backup"),
|
||||||
path(
|
path(
|
||||||
"create/backup-for-computer/<int:pk>/",
|
"create/backup-for-computer/<int:pk>/",
|
||||||
|
|
|
@ -47,7 +47,7 @@ def backup_detail_view(request, pk):
|
||||||
class BackupCreateView(LoginRequiredMixin, CreateView):
|
class BackupCreateView(LoginRequiredMixin, CreateView):
|
||||||
model = Backup
|
model = Backup
|
||||||
template_name = "backups/backup_create.html"
|
template_name = "backups/backup_create.html"
|
||||||
fields = "__all__"
|
fields = "__all__" # type: ignore
|
||||||
|
|
||||||
def get_success_url(self):
|
def get_success_url(self):
|
||||||
return reverse("computer", args=(self.computer.pk,))
|
return reverse("computer", args=(self.computer.pk,))
|
||||||
|
@ -63,7 +63,7 @@ class BackupCreateView(LoginRequiredMixin, CreateView):
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
class BackupDeleteView(LoginRequiredMixin, DeleteView):
|
class BackupDeleteView(LoginRequiredMixin, DeleteView): # type: ignore
|
||||||
model = Backup
|
model = Backup
|
||||||
template_name = "backups/backup_confirm_delete.html"
|
template_name = "backups/backup_confirm_delete.html"
|
||||||
|
|
||||||
|
@ -71,7 +71,7 @@ class BackupDeleteView(LoginRequiredMixin, DeleteView):
|
||||||
return reverse("computer", args=(self.object.computer.pk,))
|
return reverse("computer", args=(self.object.computer.pk,))
|
||||||
|
|
||||||
|
|
||||||
class BackupDeleteFromTableView(LoginRequiredMixin, DeleteView):
|
class BackupDeleteFromTableView(LoginRequiredMixin, DeleteView): # type: ignore
|
||||||
model = Backup
|
model = Backup
|
||||||
template_name = "backups/backup_confirm_delete.html"
|
template_name = "backups/backup_confirm_delete.html"
|
||||||
|
|
||||||
|
|
|
@ -26,62 +26,64 @@ from .models import (
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
class SoftwareInLine(nested_admin.NestedStackedInline):
|
class SoftwareInLine(nested_admin.NestedStackedInline): # pylint: disable=no-member
|
||||||
model = ComputerSoftwareRelation
|
model = ComputerSoftwareRelation
|
||||||
extra = 0
|
extra = 0
|
||||||
verbose_name_plural = "Software"
|
verbose_name_plural = "Software"
|
||||||
|
|
||||||
|
|
||||||
class RamInLine(nested_admin.NestedStackedInline):
|
class RamInLine(nested_admin.NestedStackedInline): # pylint: disable=no-member
|
||||||
model = ComputerRamRelation
|
model = ComputerRamRelation
|
||||||
extra = 0
|
extra = 0
|
||||||
verbose_name_plural = "RAM Modules"
|
verbose_name_plural = "RAM Modules"
|
||||||
|
|
||||||
|
|
||||||
class DiskInLine(nested_admin.NestedStackedInline):
|
class DiskInLine(nested_admin.NestedStackedInline): # pylint: disable=no-member
|
||||||
model = ComputerDiskRelation
|
model = ComputerDiskRelation
|
||||||
extra = 0
|
extra = 0
|
||||||
verbose_name_plural = "Disks"
|
verbose_name_plural = "Disks"
|
||||||
|
|
||||||
|
|
||||||
class DisksInRaidInLine(nested_admin.NestedStackedInline):
|
class DisksInRaidInLine(nested_admin.NestedStackedInline): # pylint: disable=no-member
|
||||||
model = DisksInRaid
|
model = DisksInRaid
|
||||||
extra = 0
|
extra = 0
|
||||||
verbose_name_plural = "Disks in RAID"
|
verbose_name_plural = "Disks in RAID"
|
||||||
|
|
||||||
|
|
||||||
class CpusInLine(nested_admin.NestedStackedInline):
|
class CpusInLine(nested_admin.NestedStackedInline): # pylint: disable=no-member
|
||||||
model = ComputerCpuRelation
|
model = ComputerCpuRelation
|
||||||
extra = 0
|
extra = 0
|
||||||
verbose_name_plural = "CPUs"
|
verbose_name_plural = "CPUs"
|
||||||
|
|
||||||
|
|
||||||
class GpusInLine(nested_admin.NestedStackedInline):
|
class GpusInLine(nested_admin.NestedStackedInline): # pylint: disable=no-member
|
||||||
model = ComputerGpuRelation
|
model = ComputerGpuRelation
|
||||||
extra = 0
|
extra = 0
|
||||||
verbose_name_plural = "GPUs"
|
verbose_name_plural = "GPUs"
|
||||||
|
|
||||||
|
|
||||||
class RaidInLine(nested_admin.NestedStackedInline):
|
class RaidInLine(nested_admin.NestedStackedInline): # pylint: disable=no-member
|
||||||
model = Raid
|
model = Raid
|
||||||
extra = 0
|
extra = 0
|
||||||
verbose_name_plural = "RAID"
|
verbose_name_plural = "RAID"
|
||||||
inlines = (DisksInRaidInLine,)
|
inlines = (DisksInRaidInLine,)
|
||||||
|
|
||||||
|
|
||||||
class DeviceInNetInline(nested_admin.NestedStackedInline):
|
class DeviceInNetInline(nested_admin.NestedStackedInline): # pylint: disable=no-member
|
||||||
model = DeviceInNet
|
model = DeviceInNet
|
||||||
extra = 0
|
extra = 0
|
||||||
verbose_name_plural = "Nets"
|
verbose_name_plural = "Nets"
|
||||||
|
|
||||||
|
|
||||||
class LicenseWithComputerInLine(nested_admin.NestedStackedInline):
|
class LicenseWithComputerInLine(
|
||||||
|
nested_admin.NestedStackedInline
|
||||||
|
): # pylint: disable=no-member
|
||||||
model = LicenseWithComputer
|
model = LicenseWithComputer
|
||||||
extra = 0
|
extra = 0
|
||||||
verbose_name_plural = "Licenses"
|
verbose_name_plural = "Licenses"
|
||||||
|
|
||||||
|
|
||||||
class ComputerAdmin(nested_admin.NestedModelAdmin):
|
class ComputerAdmin(nested_admin.NestedModelAdmin): # pylint: disable=no-member
|
||||||
list_display = ("name", "host")
|
list_display = ("name", "host")
|
||||||
inlines = (
|
inlines = (
|
||||||
SoftwareInLine,
|
SoftwareInLine,
|
||||||
|
|
|
@ -41,15 +41,9 @@ class ComputerUpdateForm(forms.ModelForm):
|
||||||
|
|
||||||
def __init__(self, request, *args, **kwargs):
|
def __init__(self, request, *args, **kwargs):
|
||||||
super(ComputerUpdateForm, self).__init__(*args, **kwargs)
|
super(ComputerUpdateForm, self).__init__(*args, **kwargs)
|
||||||
customers = utils.objects_for_allowed_customers(
|
customers = utils.objects_for_allowed_customers(Customer, user=request.user)
|
||||||
Customer, user=request.user
|
locations = utils.objects_for_allowed_customers(Location, user=request.user)
|
||||||
)
|
hosts = utils.objects_for_allowed_customers(Computer, user=request.user)
|
||||||
locations = utils.objects_for_allowed_customers(
|
|
||||||
Location, user=request.user
|
|
||||||
)
|
|
||||||
hosts = utils.objects_for_allowed_customers(
|
|
||||||
Computer, user=request.user
|
|
||||||
)
|
|
||||||
users = utils.objects_for_allowed_customers(User, user=request.user)
|
users = utils.objects_for_allowed_customers(User, user=request.user)
|
||||||
self.fields["customer"].queryset = customers
|
self.fields["customer"].queryset = customers
|
||||||
self.fields["location"].queryset = locations
|
self.fields["location"].queryset = locations
|
||||||
|
|
|
@ -23,12 +23,8 @@ class Computer(Device):
|
||||||
ram = models.ManyToManyField(Ram, through="ComputerRamRelation")
|
ram = models.ManyToManyField(Ram, through="ComputerRamRelation")
|
||||||
gpu = models.ManyToManyField(Gpu, through="ComputerGpuRelation")
|
gpu = models.ManyToManyField(Gpu, through="ComputerGpuRelation")
|
||||||
disks = models.ManyToManyField(Disk, through="ComputerDiskRelation")
|
disks = models.ManyToManyField(Disk, through="ComputerDiskRelation")
|
||||||
software = models.ManyToManyField(
|
software = models.ManyToManyField(Software, through="ComputerSoftwareRelation")
|
||||||
Software, through="ComputerSoftwareRelation"
|
host = models.ForeignKey("self", null=True, blank=True, on_delete=models.CASCADE)
|
||||||
)
|
|
||||||
host = models.ForeignKey(
|
|
||||||
"self", null=True, blank=True, on_delete=models.CASCADE
|
|
||||||
)
|
|
||||||
allocated_space = models.IntegerField(null=True, blank=True)
|
allocated_space = models.IntegerField(null=True, blank=True)
|
||||||
|
|
||||||
def __str__(self):
|
def __str__(self):
|
||||||
|
|
|
@ -12,9 +12,7 @@ class RaidType(Category):
|
||||||
|
|
||||||
class Raid(models.Model):
|
class Raid(models.Model):
|
||||||
usable_space = models.IntegerField(blank=True, null=True)
|
usable_space = models.IntegerField(blank=True, null=True)
|
||||||
raid_type = models.ForeignKey(
|
raid_type = models.ForeignKey(RaidType, models.SET_NULL, blank=True, null=True)
|
||||||
RaidType, models.SET_NULL, blank=True, null=True
|
|
||||||
)
|
|
||||||
computer = models.ForeignKey(Computer, on_delete=models.CASCADE)
|
computer = models.ForeignKey(Computer, on_delete=models.CASCADE)
|
||||||
|
|
||||||
def __str__(self):
|
def __str__(self):
|
||||||
|
|
|
@ -15,15 +15,11 @@ def test_computer_detail_view_not_logged_in():
|
||||||
|
|
||||||
def test_computer_detail_view(create_admin_user):
|
def test_computer_detail_view(create_admin_user):
|
||||||
create_admin_user()
|
create_admin_user()
|
||||||
computer = mixer.blend(
|
computer = mixer.blend("computers.Computer", customer=mixer.SELECT, os=mixer.SELECT)
|
||||||
"computers.Computer", customer=mixer.SELECT, os=mixer.SELECT
|
|
||||||
)
|
|
||||||
client = Client()
|
client = Client()
|
||||||
client.login(username="pharma-admin", password="password")
|
client.login(username="pharma-admin", password="password")
|
||||||
response = client.get("/computer/" + str(computer.id) + "/")
|
response = client.get("/computer/" + str(computer.id) + "/")
|
||||||
assert response.status_code == 200 and helper.in_content(
|
assert response.status_code == 200 and helper.in_content(response, computer)
|
||||||
response, computer
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def test_computer_detail_view_not_found(create_admin_user):
|
def test_computer_detail_view_not_found(create_admin_user):
|
||||||
|
@ -43,9 +39,7 @@ def test_computer_detail_view_ram_relation(create_admin_user):
|
||||||
client = Client()
|
client = Client()
|
||||||
client.login(username="pharma-admin", password="password")
|
client.login(username="pharma-admin", password="password")
|
||||||
response = client.get("/computer/" + str(computer.id) + "/")
|
response = client.get("/computer/" + str(computer.id) + "/")
|
||||||
assert response.status_code == 200 and helper.in_content(
|
assert response.status_code == 200 and helper.in_content(response, "RAM Modules:")
|
||||||
response, "RAM Modules:"
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def test_computer_detail_view_raid_relation(create_admin_user):
|
def test_computer_detail_view_raid_relation(create_admin_user):
|
||||||
|
@ -53,9 +47,7 @@ def test_computer_detail_view_raid_relation(create_admin_user):
|
||||||
computer = mixer.blend("computers.Computer", customer=mixer.SELECT)
|
computer = mixer.blend("computers.Computer", customer=mixer.SELECT)
|
||||||
raid_type = mixer.blend("computers.RaidType")
|
raid_type = mixer.blend("computers.RaidType")
|
||||||
disk = mixer.blend("computers.Disk")
|
disk = mixer.blend("computers.Disk")
|
||||||
raid = mixer.blend(
|
raid = mixer.blend("computers.Raid", computer=computer, raid_type=raid_type)
|
||||||
"computers.Raid", computer=computer, raid_type=raid_type
|
|
||||||
)
|
|
||||||
mixer.blend("computers.DisksInRaid", raid=raid, disk=disk)
|
mixer.blend("computers.DisksInRaid", raid=raid, disk=disk)
|
||||||
client = Client()
|
client = Client()
|
||||||
client.login(username="pharma-admin", password="password")
|
client.login(username="pharma-admin", password="password")
|
||||||
|
|
|
@ -12,9 +12,7 @@ def test_computer_create_form(create_admin_user):
|
||||||
fixture = create_admin_user()
|
fixture = create_admin_user()
|
||||||
user = mixer.blend("core.InventoryUser", customer=fixture["customer"])
|
user = mixer.blend("core.InventoryUser", customer=fixture["customer"])
|
||||||
form = forms.ComputerCreateForm(user=user, data={})
|
form = forms.ComputerCreateForm(user=user, data={})
|
||||||
assert (
|
assert form.is_valid() is False, "Should be false because no data was given"
|
||||||
form.is_valid() is False
|
|
||||||
), "Should be false because no data was given"
|
|
||||||
|
|
||||||
data = {"name": "pharma-pc1", "customer": 3}
|
data = {"name": "pharma-pc1", "customer": 3}
|
||||||
form = forms.ComputerCreateForm(user=user, data=data)
|
form = forms.ComputerCreateForm(user=user, data=data)
|
||||||
|
@ -32,9 +30,7 @@ def test_computer_update_form(create_admin_user):
|
||||||
request = HttpRequest()
|
request = HttpRequest()
|
||||||
request.user = fixture["admin"]
|
request.user = fixture["admin"]
|
||||||
form = forms.ComputerUpdateForm(request, data={})
|
form = forms.ComputerUpdateForm(request, data={})
|
||||||
assert (
|
assert form.is_valid() is False, "Should be false because no data was given"
|
||||||
form.is_valid() is False
|
|
||||||
), "Should be false because no data was given"
|
|
||||||
|
|
||||||
data = {"name": "pharma-pc1", "customer": 20356}
|
data = {"name": "pharma-pc1", "customer": 20356}
|
||||||
form = forms.ComputerUpdateForm(request, data=data)
|
form = forms.ComputerUpdateForm(request, data=data)
|
||||||
|
|
|
@ -27,6 +27,4 @@ def test_computer_list_view(create_admin_user):
|
||||||
client = Client()
|
client = Client()
|
||||||
client.login(username="pharma-admin", password="password")
|
client.login(username="pharma-admin", password="password")
|
||||||
response = client.get("/computers/all/")
|
response = client.get("/computers/all/")
|
||||||
assert response.status_code == 200 and helper.in_content(
|
assert response.status_code == 200 and helper.in_content(response, computer)
|
||||||
response, computer
|
|
||||||
)
|
|
||||||
|
|
|
@ -21,9 +21,7 @@ def test_customer_computer_table(create_admin_user):
|
||||||
client.login(username="pharma-admin", password="password")
|
client.login(username="pharma-admin", password="password")
|
||||||
computer = mixer.blend("computers.Computer", customer=mixer.SELECT)
|
computer = mixer.blend("computers.Computer", customer=mixer.SELECT)
|
||||||
response = client.get("/customer/" + str(customer.id) + "/computers/")
|
response = client.get("/customer/" + str(customer.id) + "/computers/")
|
||||||
assert response.status_code == 200 and helper.in_content(
|
assert response.status_code == 200 and helper.in_content(response, computer)
|
||||||
response, computer
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def test_customer_computer_table_no_computer(create_admin_user):
|
def test_customer_computer_table_no_computer(create_admin_user):
|
||||||
|
|
|
@ -41,9 +41,7 @@ from .tables import ComputersTable
|
||||||
|
|
||||||
@login_required
|
@login_required
|
||||||
def computer_detail_view(request, pk):
|
def computer_detail_view(request, pk):
|
||||||
device = utils.get_object_with_view_permission(
|
device = utils.get_object_with_view_permission(Computer, user=request.user, pk=pk)
|
||||||
Computer, user=request.user, pk=pk
|
|
||||||
)
|
|
||||||
disks_relations = ComputerDiskRelation.objects.filter(computer=pk)
|
disks_relations = ComputerDiskRelation.objects.filter(computer=pk)
|
||||||
warranty_relations = Warranty.objects.filter(device=pk)
|
warranty_relations = Warranty.objects.filter(device=pk)
|
||||||
ram_relations = ComputerRamRelation.objects.filter(computer=pk)
|
ram_relations = ComputerRamRelation.objects.filter(computer=pk)
|
||||||
|
@ -76,9 +74,7 @@ def computer_detail_view(request, pk):
|
||||||
@login_required
|
@login_required
|
||||||
def computers_table_view(request, pk):
|
def computers_table_view(request, pk):
|
||||||
table = ComputersTable(
|
table = ComputersTable(
|
||||||
utils.get_objects_for_customer(
|
utils.get_objects_for_customer(Computer, user=request.user, customer_pk=pk)
|
||||||
Computer, user=request.user, customer_pk=pk
|
|
||||||
)
|
|
||||||
)
|
)
|
||||||
RequestConfig(request).configure(table)
|
RequestConfig(request).configure(table)
|
||||||
return render(
|
return render(
|
||||||
|
@ -139,9 +135,7 @@ def computer_update_view(request, pk):
|
||||||
A view to create a customer.
|
A view to create a customer.
|
||||||
"""
|
"""
|
||||||
template_name = "computers/computer_update.html"
|
template_name = "computers/computer_update.html"
|
||||||
computer = utils.get_object_with_view_permission(
|
computer = utils.get_object_with_view_permission(Computer, user=request.user, pk=pk)
|
||||||
Computer, user=request.user, pk=pk
|
|
||||||
)
|
|
||||||
if request.method == "POST":
|
if request.method == "POST":
|
||||||
form = ComputerUpdateForm(request, request.POST, instance=computer)
|
form = ComputerUpdateForm(request, request.POST, instance=computer)
|
||||||
if form.is_valid():
|
if form.is_valid():
|
||||||
|
@ -152,7 +146,7 @@ def computer_update_view(request, pk):
|
||||||
return TemplateResponse(request, template_name, {"form": form})
|
return TemplateResponse(request, template_name, {"form": form})
|
||||||
|
|
||||||
|
|
||||||
class ComputerDeleteView(LoginRequiredMixin, DeleteView):
|
class ComputerDeleteView(LoginRequiredMixin, DeleteView): # type: ignore
|
||||||
model = Computer
|
model = Computer
|
||||||
|
|
||||||
def get_success_url(self):
|
def get_success_url(self):
|
||||||
|
@ -178,7 +172,7 @@ class ComputerRamRelationCreateView(LoginRequiredMixin, CreateView):
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
class ComputerRamRelationDeleteView(LoginRequiredMixin, DeleteView):
|
class ComputerRamRelationDeleteView(LoginRequiredMixin, DeleteView): # type: ignore
|
||||||
model = ComputerRamRelation
|
model = ComputerRamRelation
|
||||||
template_name = "computers/relation_confirm_delete.html"
|
template_name = "computers/relation_confirm_delete.html"
|
||||||
|
|
||||||
|
@ -205,7 +199,7 @@ class ComputerCpuRelationCreateView(LoginRequiredMixin, CreateView):
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
class ComputerCpuRelationDeleteView(LoginRequiredMixin, DeleteView):
|
class ComputerCpuRelationDeleteView(LoginRequiredMixin, DeleteView): # type: ignore
|
||||||
model = ComputerCpuRelation
|
model = ComputerCpuRelation
|
||||||
template_name = "computers/relation_confirm_delete.html"
|
template_name = "computers/relation_confirm_delete.html"
|
||||||
|
|
||||||
|
@ -232,7 +226,7 @@ class ComputerGpuRelationCreateView(LoginRequiredMixin, CreateView):
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
class ComputerGpuRelationDeleteView(LoginRequiredMixin, DeleteView):
|
class ComputerGpuRelationDeleteView(LoginRequiredMixin, DeleteView): # type: ignore
|
||||||
model = ComputerGpuRelation
|
model = ComputerGpuRelation
|
||||||
template_name = "computers/relation_confirm_delete.html"
|
template_name = "computers/relation_confirm_delete.html"
|
||||||
|
|
||||||
|
@ -259,7 +253,7 @@ class ComputerDiskRelationCreateView(LoginRequiredMixin, CreateView):
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
class ComputerDiskRelationDeleteView(LoginRequiredMixin, DeleteView):
|
class ComputerDiskRelationDeleteView(LoginRequiredMixin, DeleteView): # type: ignore
|
||||||
model = ComputerDiskRelation
|
model = ComputerDiskRelation
|
||||||
template_name = "computers/relation_confirm_delete.html"
|
template_name = "computers/relation_confirm_delete.html"
|
||||||
|
|
||||||
|
@ -286,7 +280,7 @@ class ComputerSoftwareRelationCreateView(LoginRequiredMixin, CreateView):
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
class ComputerSoftwareRelationDeleteView(LoginRequiredMixin, DeleteView):
|
class ComputerSoftwareRelationDeleteView(LoginRequiredMixin, DeleteView): # type: ignore
|
||||||
model = ComputerSoftwareRelation
|
model = ComputerSoftwareRelation
|
||||||
template_name = "computers/relation_confirm_delete.html"
|
template_name = "computers/relation_confirm_delete.html"
|
||||||
|
|
||||||
|
@ -313,7 +307,7 @@ class RaidCreateView(LoginRequiredMixin, CreateView):
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
class RaidDeleteView(LoginRequiredMixin, DeleteView):
|
class RaidDeleteView(LoginRequiredMixin, DeleteView): # type: ignore
|
||||||
model = Raid
|
model = Raid
|
||||||
template_name = "computers/relation_confirm_delete.html"
|
template_name = "computers/relation_confirm_delete.html"
|
||||||
|
|
||||||
|
|
|
@ -22,9 +22,7 @@ def django_db_setup(django_db_setup, django_db_blocker):
|
||||||
def create_admin_user():
|
def create_admin_user():
|
||||||
def _create_admin_user():
|
def _create_admin_user():
|
||||||
User = get_user_model()
|
User = get_user_model()
|
||||||
admin = User.objects.create_user(
|
admin = User.objects.create_user("pharma-admin", "admin@pharma.com", "password")
|
||||||
"pharma-admin", "admin@pharma.com", "password"
|
|
||||||
)
|
|
||||||
customer = mixer.blend("customers.Customer")
|
customer = mixer.blend("customers.Customer")
|
||||||
group = Group.objects.create(name="Pharma Corp. Admin")
|
group = Group.objects.create(name="Pharma Corp. Admin")
|
||||||
admin.groups.add(group)
|
admin.groups.add(group)
|
||||||
|
|
|
@ -15,9 +15,7 @@ def test_get_object_with_view_permission(create_admin_user):
|
||||||
fixture = create_admin_user()
|
fixture = create_admin_user()
|
||||||
customer = fixture["customer"]
|
customer = fixture["customer"]
|
||||||
admin = fixture["admin"]
|
admin = fixture["admin"]
|
||||||
object = utils.get_object_with_view_permission(
|
object = utils.get_object_with_view_permission(Customer, user=admin, pk=customer.id)
|
||||||
Customer, user=admin, pk=customer.id
|
|
||||||
)
|
|
||||||
assert object == customer
|
assert object == customer
|
||||||
|
|
||||||
|
|
||||||
|
@ -26,9 +24,7 @@ def test_get_object_with_view_permission_device(create_admin_user):
|
||||||
customer = fixture["customer"]
|
customer = fixture["customer"]
|
||||||
admin = fixture["admin"]
|
admin = fixture["admin"]
|
||||||
device = mixer.blend(Device, customer=customer)
|
device = mixer.blend(Device, customer=customer)
|
||||||
object = utils.get_object_with_view_permission(
|
object = utils.get_object_with_view_permission(Device, user=admin, pk=device.id)
|
||||||
Device, user=admin, pk=device.id
|
|
||||||
)
|
|
||||||
assert object == device
|
assert object == device
|
||||||
|
|
||||||
|
|
||||||
|
@ -37,9 +33,7 @@ def test_get_object_without_view_permission(create_admin_user):
|
||||||
customer = mixer.blend(Customer)
|
customer = mixer.blend(Customer)
|
||||||
admin = fixture["admin"]
|
admin = fixture["admin"]
|
||||||
with pytest.raises(Http404):
|
with pytest.raises(Http404):
|
||||||
utils.get_object_with_view_permission(
|
utils.get_object_with_view_permission(Customer, user=admin, pk=customer.id)
|
||||||
Customer, user=admin, pk=customer.id
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def test_get_object_without_view_permission_device(create_admin_user):
|
def test_get_object_without_view_permission_device(create_admin_user):
|
||||||
|
|
|
@ -16,9 +16,7 @@ def test_get_objects_for_customer_with_customer(create_admin_user):
|
||||||
customer = fixture["customer"]
|
customer = fixture["customer"]
|
||||||
admin = fixture["admin"]
|
admin = fixture["admin"]
|
||||||
with pytest.raises(Exception):
|
with pytest.raises(Exception):
|
||||||
utils.get_objects_for_customer(
|
utils.get_objects_for_customer(Customer, user=admin, customer_pk=customer.id)
|
||||||
Customer, user=admin, customer_pk=customer.id
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def test_get_objects_for_customer_device(create_admin_user):
|
def test_get_objects_for_customer_device(create_admin_user):
|
||||||
|
@ -37,9 +35,7 @@ def test_get_all_objects_for_unallowed_customers(create_admin_user):
|
||||||
customer = mixer.blend(Customer)
|
customer = mixer.blend(Customer)
|
||||||
admin = fixture["admin"]
|
admin = fixture["admin"]
|
||||||
with pytest.raises(Http404):
|
with pytest.raises(Http404):
|
||||||
utils.get_objects_for_customer(
|
utils.get_objects_for_customer(Customer, user=admin, customer_pk=customer.id)
|
||||||
Customer, user=admin, customer_pk=customer.id
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def test_get_all_objects_for_unallowed_customers_device(create_admin_user):
|
def test_get_all_objects_for_unallowed_customers_device(create_admin_user):
|
||||||
|
@ -48,6 +44,4 @@ def test_get_all_objects_for_unallowed_customers_device(create_admin_user):
|
||||||
admin = fixture["admin"]
|
admin = fixture["admin"]
|
||||||
mixer.blend(Device, customer=customer)
|
mixer.blend(Device, customer=customer)
|
||||||
with pytest.raises(Http404):
|
with pytest.raises(Http404):
|
||||||
utils.get_objects_for_customer(
|
utils.get_objects_for_customer(Device, user=admin, customer_pk=customer.id)
|
||||||
Device, user=admin, customer_pk=customer.id
|
|
||||||
)
|
|
||||||
|
|
|
@ -34,9 +34,7 @@ def _get_customers(user):
|
||||||
|
|
||||||
user : django.contrib.auth.models.User
|
user : django.contrib.auth.models.User
|
||||||
"""
|
"""
|
||||||
return get_objects_for_user(
|
return get_objects_for_user(user, "customers.view_customer", klass=Customer)
|
||||||
user, "customers.view_customer", klass=Customer
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def get_object_with_view_permission(model, user=None, pk=None):
|
def get_object_with_view_permission(model, user=None, pk=None):
|
||||||
|
|
|
@ -10,8 +10,6 @@ def customer_view_permission(old_function):
|
||||||
if user.has_perm("customers.view_customer", customer):
|
if user.has_perm("customers.view_customer", customer):
|
||||||
return old_function(request, pk)
|
return old_function(request, pk)
|
||||||
else:
|
else:
|
||||||
return HttpResponseForbidden(
|
return HttpResponseForbidden("You're not allowed to access this page.")
|
||||||
"You're not allowed to access this page."
|
|
||||||
)
|
|
||||||
|
|
||||||
return new_function
|
return new_function
|
||||||
|
|
|
@ -43,4 +43,4 @@ class DummyLocation(models.Model):
|
||||||
location = models.ForeignKey(Location, on_delete=models.CASCADE)
|
location = models.ForeignKey(Location, on_delete=models.CASCADE)
|
||||||
|
|
||||||
def __str__(self):
|
def __str__(self):
|
||||||
return self.location
|
return self.location.name
|
||||||
|
|
|
@ -6,9 +6,7 @@ from core.tables import CoreTable
|
||||||
|
|
||||||
class CustomersTable(CoreTable):
|
class CustomersTable(CoreTable):
|
||||||
name = tables.LinkColumn("customer", args=[A("pk")])
|
name = tables.LinkColumn("customer", args=[A("pk")])
|
||||||
nets = tables.LinkColumn(
|
nets = tables.LinkColumn("nets", text="Nets", args=[A("pk")], orderable=False)
|
||||||
"nets", text="Nets", args=[A("pk")], orderable=False
|
|
||||||
)
|
|
||||||
computers = tables.LinkColumn(
|
computers = tables.LinkColumn(
|
||||||
"computers", text="Computers", args=[A("pk")], orderable=False
|
"computers", text="Computers", args=[A("pk")], orderable=False
|
||||||
)
|
)
|
||||||
|
@ -21,12 +19,8 @@ class CustomersTable(CoreTable):
|
||||||
licenses = tables.LinkColumn(
|
licenses = tables.LinkColumn(
|
||||||
"licenses", text="Licenses", args=[A("pk")], orderable=False
|
"licenses", text="Licenses", args=[A("pk")], orderable=False
|
||||||
)
|
)
|
||||||
users = tables.LinkColumn(
|
users = tables.LinkColumn("users", text="Users", args=[A("pk")], orderable=False)
|
||||||
"users", text="Users", args=[A("pk")], orderable=False
|
groups = tables.LinkColumn("groups", text="Groups", args=[A("pk")], orderable=False)
|
||||||
)
|
|
||||||
groups = tables.LinkColumn(
|
|
||||||
"groups", text="Groups", args=[A("pk")], orderable=False
|
|
||||||
)
|
|
||||||
project_manager = tables.Column(verbose_name="Project Manager")
|
project_manager = tables.Column(verbose_name="Project Manager")
|
||||||
delete = tables.LinkColumn(
|
delete = tables.LinkColumn(
|
||||||
"customer_delete",
|
"customer_delete",
|
||||||
|
|
|
@ -42,24 +42,12 @@ def test_customer_list_view(create_admin_user):
|
||||||
assert (
|
assert (
|
||||||
response.status_code == 200
|
response.status_code == 200
|
||||||
and helper.in_content(response, customer)
|
and helper.in_content(response, customer)
|
||||||
and helper.in_content(
|
and helper.in_content(response, "/customer/" + str(customer.id) + "/nets/")
|
||||||
response, "/customer/" + str(customer.id) + "/nets/"
|
and helper.in_content(response, "/customer/" + str(customer.id) + "/computers/")
|
||||||
)
|
and helper.in_content(response, "/customer/" + str(customer.id) + "/devices/")
|
||||||
and helper.in_content(
|
and helper.in_content(response, "/customer/" + str(customer.id) + "/backups/")
|
||||||
response, "/customer/" + str(customer.id) + "/computers/"
|
and helper.in_content(response, "/customer/" + str(customer.id) + "/licenses/")
|
||||||
)
|
and helper.in_content(response, "/customer/" + str(customer.id) + "/users/")
|
||||||
and helper.in_content(
|
|
||||||
response, "/customer/" + str(customer.id) + "/devices/"
|
|
||||||
)
|
|
||||||
and helper.in_content(
|
|
||||||
response, "/customer/" + str(customer.id) + "/backups/"
|
|
||||||
)
|
|
||||||
and helper.in_content(
|
|
||||||
response, "/customer/" + str(customer.id) + "/licenses/"
|
|
||||||
)
|
|
||||||
and helper.in_content(
|
|
||||||
response, "/customer/" + str(customer.id) + "/users/"
|
|
||||||
)
|
|
||||||
and helper.in_content(response, project_manager)
|
and helper.in_content(response, project_manager)
|
||||||
)
|
)
|
||||||
|
|
||||||
|
@ -75,41 +63,21 @@ def test_customer_list_view_multiple_customers(create_admin_user):
|
||||||
assert (
|
assert (
|
||||||
response.status_code == 200
|
response.status_code == 200
|
||||||
and helper.in_content(response, customer1)
|
and helper.in_content(response, customer1)
|
||||||
and helper.in_content(
|
and helper.in_content(response, "/customer/" + str(customer1.id) + "/nets/")
|
||||||
response, "/customer/" + str(customer1.id) + "/nets/"
|
|
||||||
)
|
|
||||||
and helper.in_content(
|
and helper.in_content(
|
||||||
response, "/customer/" + str(customer1.id) + "/computers/"
|
response, "/customer/" + str(customer1.id) + "/computers/"
|
||||||
)
|
)
|
||||||
and helper.in_content(
|
and helper.in_content(response, "/customer/" + str(customer1.id) + "/devices/")
|
||||||
response, "/customer/" + str(customer1.id) + "/devices/"
|
and helper.in_content(response, "/customer/" + str(customer1.id) + "/backups/")
|
||||||
)
|
and helper.in_content(response, "/customer/" + str(customer1.id) + "/licenses/")
|
||||||
and helper.in_content(
|
and helper.in_content(response, "/customer/" + str(customer1.id) + "/users/")
|
||||||
response, "/customer/" + str(customer1.id) + "/backups/"
|
|
||||||
)
|
|
||||||
and helper.in_content(
|
|
||||||
response, "/customer/" + str(customer1.id) + "/licenses/"
|
|
||||||
)
|
|
||||||
and helper.in_content(
|
|
||||||
response, "/customer/" + str(customer1.id) + "/users/"
|
|
||||||
)
|
|
||||||
and helper.in_content(response, customer2)
|
and helper.in_content(response, customer2)
|
||||||
and helper.in_content(
|
and helper.in_content(response, "/customer/" + str(customer2.id) + "/nets/")
|
||||||
response, "/customer/" + str(customer2.id) + "/nets/"
|
|
||||||
)
|
|
||||||
and helper.in_content(
|
and helper.in_content(
|
||||||
response, "/customer/" + str(customer2.id) + "/computers/"
|
response, "/customer/" + str(customer2.id) + "/computers/"
|
||||||
)
|
)
|
||||||
and helper.in_content(
|
and helper.in_content(response, "/customer/" + str(customer2.id) + "/devices/")
|
||||||
response, "/customer/" + str(customer2.id) + "/devices/"
|
and helper.in_content(response, "/customer/" + str(customer2.id) + "/backups/")
|
||||||
)
|
and helper.in_content(response, "/customer/" + str(customer2.id) + "/licenses/")
|
||||||
and helper.in_content(
|
and helper.in_content(response, "/customer/" + str(customer1.id) + "/users/")
|
||||||
response, "/customer/" + str(customer2.id) + "/backups/"
|
|
||||||
)
|
|
||||||
and helper.in_content(
|
|
||||||
response, "/customer/" + str(customer2.id) + "/licenses/"
|
|
||||||
)
|
|
||||||
and helper.in_content(
|
|
||||||
response, "/customer/" + str(customer1.id) + "/users/"
|
|
||||||
)
|
|
||||||
)
|
)
|
||||||
|
|
|
@ -10,9 +10,7 @@ def test_location_form(create_admin_user):
|
||||||
fixture = create_admin_user()
|
fixture = create_admin_user()
|
||||||
user = fixture["admin"]
|
user = fixture["admin"]
|
||||||
form = forms.LocationForm(user=user, data={})
|
form = forms.LocationForm(user=user, data={})
|
||||||
assert (
|
assert form.is_valid() is False, "Should be false because no data was given"
|
||||||
form.is_valid() is False
|
|
||||||
), "Should be false because no data was given"
|
|
||||||
|
|
||||||
data = {"name": "Main Office", "customer": 3}
|
data = {"name": "Main Office", "customer": 3}
|
||||||
form = forms.LocationForm(user=user, data=data)
|
form = forms.LocationForm(user=user, data=data)
|
||||||
|
|
|
@ -14,9 +14,7 @@ def test_load_htmx_create_location_view(create_admin_user):
|
||||||
client.login(username="pharma-admin", password="password")
|
client.login(username="pharma-admin", password="password")
|
||||||
url = "/create/location/"
|
url = "/create/location/"
|
||||||
response = client.get(url)
|
response = client.get(url)
|
||||||
assert response.status_code == 200 and helper.in_content(
|
assert response.status_code == 200 and helper.in_content(response, "Add Location")
|
||||||
response, "Add Location"
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def test_htmx_create_location_view(create_admin_user):
|
def test_htmx_create_location_view(create_admin_user):
|
||||||
|
@ -25,9 +23,7 @@ def test_htmx_create_location_view(create_admin_user):
|
||||||
client.login(username="pharma-admin", password="password")
|
client.login(username="pharma-admin", password="password")
|
||||||
data = {"name": mixer.faker.name(), "save_location": 1}
|
data = {"name": mixer.faker.name(), "save_location": 1}
|
||||||
response = client.post("/create/location/", data)
|
response = client.post("/create/location/", data)
|
||||||
assert response.status_code == 200 and helper.in_content(
|
assert response.status_code == 200 and helper.in_content(response, data["name"])
|
||||||
response, data["name"]
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def test_htmx_create_location_view_invalid_form(create_admin_user):
|
def test_htmx_create_location_view_invalid_form(create_admin_user):
|
||||||
|
|
|
@ -24,9 +24,7 @@ def customers_table_view(request):
|
||||||
customers = utils.objects_for_allowed_customers(Customer, request.user)
|
customers = utils.objects_for_allowed_customers(Customer, request.user)
|
||||||
table = CustomersTable(customers)
|
table = CustomersTable(customers)
|
||||||
RequestConfig(request).configure(table)
|
RequestConfig(request).configure(table)
|
||||||
return render(
|
return render(request, "customers/customer_list.html", {"customers": table})
|
||||||
request, "customers/customer_list.html", {"customers": table}
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
@login_required
|
@login_required
|
||||||
|
@ -44,23 +42,17 @@ def create_customer(request):
|
||||||
)
|
)
|
||||||
form = CustomerForm()
|
form = CustomerForm()
|
||||||
context = {"form": form}
|
context = {"form": form}
|
||||||
return TemplateResponse(
|
return TemplateResponse(request, "customers/partials/customer_create.html", context)
|
||||||
request, "customers/partials/customer_create.html", context
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
@login_required
|
@login_required
|
||||||
def customer_detail_view(request, pk):
|
def customer_detail_view(request, pk):
|
||||||
customer = utils.get_object_with_view_permission(
|
customer = utils.get_object_with_view_permission(Customer, user=request.user, pk=pk)
|
||||||
Customer, user=request.user, pk=pk
|
|
||||||
)
|
|
||||||
context = {"customer": customer}
|
context = {"customer": customer}
|
||||||
return TemplateResponse(
|
return TemplateResponse(request, "customers/customer_details.html", context)
|
||||||
request, "customers/customer_details.html", context
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
class CustomerDeleteView(LoginRequiredMixin, DeleteView):
|
class CustomerDeleteView(LoginRequiredMixin, DeleteView): # type: ignore
|
||||||
model = Customer
|
model = Customer
|
||||||
|
|
||||||
def get_success_url(self):
|
def get_success_url(self):
|
||||||
|
|
|
@ -12,13 +12,13 @@ from .models import (
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
class DeviceInNetInline(nested_admin.NestedStackedInline):
|
class DeviceInNetInline(nested_admin.NestedStackedInline): # pylint: disable=no-member
|
||||||
model = DeviceInNet
|
model = DeviceInNet
|
||||||
extra = 0
|
extra = 0
|
||||||
verbose_name_plural = "Nets"
|
verbose_name_plural = "Nets"
|
||||||
|
|
||||||
|
|
||||||
class DeviceAdmin(nested_admin.NestedModelAdmin):
|
class DeviceAdmin(nested_admin.NestedModelAdmin): # pylint: disable=no-member
|
||||||
inlines = (DeviceInNetInline,)
|
inlines = (DeviceInNetInline,)
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -11,8 +11,6 @@ def device_view_permission(old_function):
|
||||||
if user.has_perm("customers.view_customer", device.customer):
|
if user.has_perm("customers.view_customer", device.customer):
|
||||||
return old_function(request, pk)
|
return old_function(request, pk)
|
||||||
else:
|
else:
|
||||||
return HttpResponseForbidden(
|
return HttpResponseForbidden("You're not allowed to access this device.")
|
||||||
"You're not allowed to access this device."
|
|
||||||
)
|
|
||||||
|
|
||||||
return new_function
|
return new_function
|
||||||
|
|
|
@ -69,12 +69,8 @@ class DeviceUpdateForm(forms.ModelForm):
|
||||||
|
|
||||||
def __init__(self, request, *args, **kwargs):
|
def __init__(self, request, *args, **kwargs):
|
||||||
super(DeviceUpdateForm, self).__init__(*args, **kwargs)
|
super(DeviceUpdateForm, self).__init__(*args, **kwargs)
|
||||||
customers = utils.objects_for_allowed_customers(
|
customers = utils.objects_for_allowed_customers(Customer, user=request.user)
|
||||||
Customer, user=request.user
|
locations = utils.objects_for_allowed_customers(Location, user=request.user)
|
||||||
)
|
|
||||||
locations = utils.objects_for_allowed_customers(
|
|
||||||
Location, user=request.user
|
|
||||||
)
|
|
||||||
users = utils.objects_for_allowed_customers(User, user=request.user)
|
users = utils.objects_for_allowed_customers(User, user=request.user)
|
||||||
self.fields["customer"].queryset = customers
|
self.fields["customer"].queryset = customers
|
||||||
self.fields["location"].queryset = locations
|
self.fields["location"].queryset = locations
|
||||||
|
|
|
@ -38,9 +38,7 @@ class DeviceCategory(Category):
|
||||||
|
|
||||||
class HardwareModel(models.Model):
|
class HardwareModel(models.Model):
|
||||||
name = models.CharField(max_length=50)
|
name = models.CharField(max_length=50)
|
||||||
manufacturer = models.ForeignKey(
|
manufacturer = models.ForeignKey(DeviceManufacturer, on_delete=models.CASCADE)
|
||||||
DeviceManufacturer, on_delete=models.CASCADE
|
|
||||||
)
|
|
||||||
|
|
||||||
class Meta:
|
class Meta:
|
||||||
ordering = ["name"]
|
ordering = ["name"]
|
||||||
|
@ -56,19 +54,13 @@ class Device(models.Model):
|
||||||
category = models.ForeignKey(
|
category = models.ForeignKey(
|
||||||
DeviceCategory, on_delete=models.SET_NULL, null=True, blank=True
|
DeviceCategory, on_delete=models.SET_NULL, null=True, blank=True
|
||||||
)
|
)
|
||||||
owner = models.ForeignKey(
|
owner = models.ForeignKey(Owner, on_delete=models.SET_NULL, null=True, blank=True)
|
||||||
Owner, on_delete=models.SET_NULL, null=True, blank=True
|
|
||||||
)
|
|
||||||
customer = models.ForeignKey(Customer, on_delete=models.CASCADE)
|
customer = models.ForeignKey(Customer, on_delete=models.CASCADE)
|
||||||
manufacturer = models.ForeignKey(
|
manufacturer = models.ForeignKey(
|
||||||
DeviceManufacturer, models.SET_NULL, null=True, blank=True
|
DeviceManufacturer, models.SET_NULL, null=True, blank=True
|
||||||
)
|
)
|
||||||
model = models.ForeignKey(
|
model = models.ForeignKey(HardwareModel, models.SET_NULL, null=True, blank=True)
|
||||||
HardwareModel, models.SET_NULL, null=True, blank=True
|
location = models.ForeignKey(Location, models.SET_NULL, null=True, blank=True)
|
||||||
)
|
|
||||||
location = models.ForeignKey(
|
|
||||||
Location, models.SET_NULL, null=True, blank=True
|
|
||||||
)
|
|
||||||
user = models.ForeignKey(User, models.SET_NULL, null=True, blank=True)
|
user = models.ForeignKey(User, models.SET_NULL, null=True, blank=True)
|
||||||
installation_date = models.DateField(null=True, blank=True)
|
installation_date = models.DateField(null=True, blank=True)
|
||||||
net = models.ManyToManyField(Net, through="DeviceInNet")
|
net = models.ManyToManyField(Net, through="DeviceInNet")
|
||||||
|
|
|
@ -16,9 +16,7 @@ class WarrantyType(Category):
|
||||||
|
|
||||||
|
|
||||||
class Warranty(models.Model):
|
class Warranty(models.Model):
|
||||||
customer = models.ForeignKey(
|
customer = models.ForeignKey(Customer, on_delete=models.CASCADE, blank=True)
|
||||||
Customer, on_delete=models.CASCADE, blank=True
|
|
||||||
)
|
|
||||||
device = models.ForeignKey(Device, on_delete=models.CASCADE)
|
device = models.ForeignKey(Device, on_delete=models.CASCADE)
|
||||||
valid_from = models.DateField()
|
valid_from = models.DateField()
|
||||||
valid_until = models.DateField()
|
valid_until = models.DateField()
|
||||||
|
|
|
@ -12,9 +12,7 @@ def test_device_create_form(create_admin_user):
|
||||||
fixture = create_admin_user()
|
fixture = create_admin_user()
|
||||||
user = mixer.blend("core.InventoryUser", customer=fixture["customer"])
|
user = mixer.blend("core.InventoryUser", customer=fixture["customer"])
|
||||||
form = forms.DeviceCreateForm(user=user, data={})
|
form = forms.DeviceCreateForm(user=user, data={})
|
||||||
assert (
|
assert form.is_valid() is False, "Should be false because no data was given"
|
||||||
form.is_valid() is False
|
|
||||||
), "Should be false because no data was given"
|
|
||||||
|
|
||||||
data = {"name": "pharma-device1", "customer": 3}
|
data = {"name": "pharma-device1", "customer": 3}
|
||||||
form = forms.DeviceCreateForm(user=user, data=data)
|
form = forms.DeviceCreateForm(user=user, data=data)
|
||||||
|
@ -32,9 +30,7 @@ def test_device_update_form(create_admin_user):
|
||||||
request = HttpRequest()
|
request = HttpRequest()
|
||||||
request.user = fixture["admin"]
|
request.user = fixture["admin"]
|
||||||
form = forms.DeviceUpdateForm(request, data={})
|
form = forms.DeviceUpdateForm(request, data={})
|
||||||
assert (
|
assert form.is_valid() is False, "Should be false because no data was given"
|
||||||
form.is_valid() is False
|
|
||||||
), "Should be false because no data was given"
|
|
||||||
|
|
||||||
data = {"name": "pharma-device1", "customer": 3}
|
data = {"name": "pharma-device1", "customer": 3}
|
||||||
form = forms.DeviceUpdateForm(request, data=data)
|
form = forms.DeviceUpdateForm(request, data=data)
|
||||||
|
@ -50,9 +46,7 @@ def test_device_update_form(create_admin_user):
|
||||||
def test_device_create_form_duplicate_device(create_admin_user):
|
def test_device_create_form_duplicate_device(create_admin_user):
|
||||||
fixture = create_admin_user()
|
fixture = create_admin_user()
|
||||||
user = mixer.blend("core.InventoryUser", customer=fixture["customer"])
|
user = mixer.blend("core.InventoryUser", customer=fixture["customer"])
|
||||||
mixer.blend(
|
mixer.blend("devices.Device", name="pharma-device1", customer=fixture["customer"])
|
||||||
"devices.Device", name="pharma-device1", customer=fixture["customer"]
|
|
||||||
)
|
|
||||||
data = {"name": "pharma-device1", "customer": fixture["customer"].id}
|
data = {"name": "pharma-device1", "customer": fixture["customer"].id}
|
||||||
form = forms.DeviceCreateForm(user=user, data=data)
|
form = forms.DeviceCreateForm(user=user, data=data)
|
||||||
assert (
|
assert (
|
||||||
|
|
|
@ -35,9 +35,7 @@ def test_load_device_update_view(create_admin_user):
|
||||||
client.login(username="pharma-admin", password="password")
|
client.login(username="pharma-admin", password="password")
|
||||||
device = mixer.blend("devices.Device", customer=mixer.SELECT)
|
device = mixer.blend("devices.Device", customer=mixer.SELECT)
|
||||||
response = client.get("/update/device/{}/".format(device.pk))
|
response = client.get("/update/device/{}/".format(device.pk))
|
||||||
assert response.status_code == 200 and helper.in_content(
|
assert response.status_code == 200 and helper.in_content(response, device.name)
|
||||||
response, device.name
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def test_device_update_view(create_admin_user):
|
def test_device_update_view(create_admin_user):
|
||||||
|
@ -187,9 +185,7 @@ def test_device_in_net_update_view(create_admin_user):
|
||||||
"mac_address": "",
|
"mac_address": "",
|
||||||
"ip_status": "1",
|
"ip_status": "1",
|
||||||
}
|
}
|
||||||
response = client.post(
|
response = client.post("/update/device-in-net/{}/".format(device_in_net.pk), data)
|
||||||
"/update/device-in-net/{}/".format(device_in_net.pk), data
|
|
||||||
)
|
|
||||||
assert response.status_code == 302
|
assert response.status_code == 302
|
||||||
device_in_net.refresh_from_db()
|
device_in_net.refresh_from_db()
|
||||||
assert device_in_net.ip == data["ip"]
|
assert device_in_net.ip == data["ip"]
|
||||||
|
|
|
@ -9,9 +9,7 @@ pytestmark = pytest.mark.django_db
|
||||||
def test_warranty_create_form(create_admin_user):
|
def test_warranty_create_form(create_admin_user):
|
||||||
create_admin_user()
|
create_admin_user()
|
||||||
form = forms.WarrantyCreateForm(data={})
|
form = forms.WarrantyCreateForm(data={})
|
||||||
assert (
|
assert form.is_valid() is False, "Should be false because no data was given"
|
||||||
form.is_valid() is False
|
|
||||||
), "Should be false because no data was given"
|
|
||||||
|
|
||||||
device = mixer.blend("devices.Device")
|
device = mixer.blend("devices.Device")
|
||||||
|
|
||||||
|
@ -33,8 +31,7 @@ def test_warranty_create_form(create_admin_user):
|
||||||
form.is_valid() is False
|
form.is_valid() is False
|
||||||
), "Should be false because valid from is before valid until"
|
), "Should be false because valid from is before valid until"
|
||||||
assert (
|
assert (
|
||||||
"Valid from date must be before valid until date"
|
"Valid from date must be before valid until date" == form.errors["__all__"][0]
|
||||||
== form.errors["__all__"][0]
|
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
|
@ -51,6 +48,5 @@ def test_warranty_update_form(create_admin_user):
|
||||||
form = forms.WarrantyUpdateForm(data=data)
|
form = forms.WarrantyUpdateForm(data=data)
|
||||||
assert form.is_valid() is False
|
assert form.is_valid() is False
|
||||||
assert (
|
assert (
|
||||||
"Valid from date must be before valid until date"
|
"Valid from date must be before valid until date" == form.errors["__all__"][0]
|
||||||
== form.errors["__all__"][0]
|
|
||||||
)
|
)
|
||||||
|
|
|
@ -39,9 +39,7 @@ def test_warranties_view_plenty_of_time(create_admin_user):
|
||||||
user.save()
|
user.save()
|
||||||
device = mixer.blend("devices.Device", customer=fixture["customer"])
|
device = mixer.blend("devices.Device", customer=fixture["customer"])
|
||||||
more_than_one_year = datetime.date(datetime.today() + timedelta(400))
|
more_than_one_year = datetime.date(datetime.today() + timedelta(400))
|
||||||
mixer.blend(
|
mixer.blend("devices.Warranty", device=device, valid_until=more_than_one_year)
|
||||||
"devices.Warranty", device=device, valid_until=more_than_one_year
|
|
||||||
)
|
|
||||||
client = Client()
|
client = Client()
|
||||||
client.login(username="pharma-admin", password="password")
|
client.login(username="pharma-admin", password="password")
|
||||||
response = client.get("/warranties/")
|
response = client.get("/warranties/")
|
||||||
|
@ -77,9 +75,7 @@ def test_warranties_view_warranty_one_year_till_expiration(create_admin_user):
|
||||||
user.save()
|
user.save()
|
||||||
device = mixer.blend("devices.Device", customer=fixture["customer"])
|
device = mixer.blend("devices.Device", customer=fixture["customer"])
|
||||||
not_one_year_more = datetime.date(datetime.today() + timedelta(200))
|
not_one_year_more = datetime.date(datetime.today() + timedelta(200))
|
||||||
mixer.blend(
|
mixer.blend("devices.Warranty", device=device, valid_until=not_one_year_more)
|
||||||
"devices.Warranty", device=device, valid_until=not_one_year_more
|
|
||||||
)
|
|
||||||
client = Client()
|
client = Client()
|
||||||
client.login(username="pharma-admin", password="password")
|
client.login(username="pharma-admin", password="password")
|
||||||
response = client.get("/warranties/")
|
response = client.get("/warranties/")
|
||||||
|
|
|
@ -4,9 +4,7 @@ from . import views
|
||||||
|
|
||||||
|
|
||||||
urlpatterns = [
|
urlpatterns = [
|
||||||
path(
|
path("customer/<int:pk>/devices/", views.devices_table_view, name="devices"),
|
||||||
"customer/<int:pk>/devices/", views.devices_table_view, name="devices"
|
|
||||||
),
|
|
||||||
path("device/<int:pk>/", views.device_detail_view, name="device"),
|
path("device/<int:pk>/", views.device_detail_view, name="device"),
|
||||||
path(
|
path(
|
||||||
"manufacturer/<int:pk>/",
|
"manufacturer/<int:pk>/",
|
||||||
|
|
|
@ -60,16 +60,12 @@ def device_detail_view(request, pk):
|
||||||
def devices_table_view(request, pk):
|
def devices_table_view(request, pk):
|
||||||
table = DevicesTable(Device.objects.filter(customer=pk))
|
table = DevicesTable(Device.objects.filter(customer=pk))
|
||||||
RequestConfig(request).configure(table)
|
RequestConfig(request).configure(table)
|
||||||
return render(
|
return render(request, "devices/device_list.html", {"devices": table, "pk": pk})
|
||||||
request, "devices/device_list.html", {"devices": table, "pk": pk}
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
@login_required
|
@login_required
|
||||||
def warranties_view(request):
|
def warranties_view(request):
|
||||||
table = WarrantiesTable(
|
table = WarrantiesTable(utils.objects_for_allowed_customers(Warranty, request.user))
|
||||||
utils.objects_for_allowed_customers(Warranty, request.user)
|
|
||||||
)
|
|
||||||
RequestConfig(request).configure(table)
|
RequestConfig(request).configure(table)
|
||||||
return render(request, "devices/warranties_list.html", {"devices": table})
|
return render(request, "devices/warranties_list.html", {"devices": table})
|
||||||
|
|
||||||
|
@ -111,9 +107,7 @@ def device_update_view(request, pk):
|
||||||
"""
|
"""
|
||||||
template_name = "devices/device_update.html"
|
template_name = "devices/device_update.html"
|
||||||
request.session["device_to_update"] = pk
|
request.session["device_to_update"] = pk
|
||||||
device = utils.get_object_with_view_permission(
|
device = utils.get_object_with_view_permission(Device, user=request.user, pk=pk)
|
||||||
Device, user=request.user, pk=pk
|
|
||||||
)
|
|
||||||
if request.method == "POST" and "save_device" in request.POST:
|
if request.method == "POST" and "save_device" in request.POST:
|
||||||
form = DeviceUpdateForm(request, request.POST, instance=device)
|
form = DeviceUpdateForm(request, request.POST, instance=device)
|
||||||
if form.is_valid():
|
if form.is_valid():
|
||||||
|
@ -124,7 +118,7 @@ def device_update_view(request, pk):
|
||||||
return TemplateResponse(request, template_name, {"form": form})
|
return TemplateResponse(request, template_name, {"form": form})
|
||||||
|
|
||||||
|
|
||||||
class DeviceDeleteView(LoginRequiredMixin, DeleteView):
|
class DeviceDeleteView(LoginRequiredMixin, DeleteView): # type: ignore
|
||||||
model = Device
|
model = Device
|
||||||
|
|
||||||
def get_success_url(self):
|
def get_success_url(self):
|
||||||
|
@ -160,7 +154,7 @@ class WarrantyUpdateView(LoginRequiredMixin, UpdateView):
|
||||||
return self.request.POST.get("previous_page")
|
return self.request.POST.get("previous_page")
|
||||||
|
|
||||||
|
|
||||||
class WarrantyDeleteView(LoginRequiredMixin, DeleteView):
|
class WarrantyDeleteView(LoginRequiredMixin, DeleteView): # type: ignore
|
||||||
model = Warranty
|
model = Warranty
|
||||||
|
|
||||||
def get_success_url(self):
|
def get_success_url(self):
|
||||||
|
@ -195,7 +189,7 @@ class DeviceInNetUpdateView(LoginRequiredMixin, UpdateView):
|
||||||
return self.request.POST.get("previous_page")
|
return self.request.POST.get("previous_page")
|
||||||
|
|
||||||
|
|
||||||
class DeviceInNetDeleteView(LoginRequiredMixin, DeleteView):
|
class DeviceInNetDeleteView(LoginRequiredMixin, DeleteView): # type: ignore
|
||||||
model = DeviceInNet
|
model = DeviceInNet
|
||||||
template_name = "devices/device_in_net_confirm_delete.html"
|
template_name = "devices/device_in_net_confirm_delete.html"
|
||||||
|
|
||||||
|
|
|
@ -48,9 +48,7 @@ class LicenseWithUser(models.Model):
|
||||||
|
|
||||||
class Meta:
|
class Meta:
|
||||||
constraints = [
|
constraints = [
|
||||||
models.UniqueConstraint(
|
models.UniqueConstraint(fields=["user", "license"], name="user per license")
|
||||||
fields=["user", "license"], name="user per license"
|
|
||||||
)
|
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -61,9 +61,7 @@ def test_customer_license_table_no_license(create_admin_user):
|
||||||
client = Client()
|
client = Client()
|
||||||
client.login(username="pharma-admin", password="password")
|
client.login(username="pharma-admin", password="password")
|
||||||
response = client.get("/customer/" + str(customer.id) + "/licenses/")
|
response = client.get("/customer/" + str(customer.id) + "/licenses/")
|
||||||
assert response.status_code == 200 and helper.not_in_content(
|
assert response.status_code == 200 and helper.not_in_content(response, customer)
|
||||||
response, customer
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def test_customer_license_table_no_permission(create_admin_user):
|
def test_customer_license_table_no_permission(create_admin_user):
|
||||||
|
|
|
@ -41,7 +41,7 @@ def licenses_table_view(request, pk):
|
||||||
class LicenseWithComputerCreateView(LoginRequiredMixin, CreateView):
|
class LicenseWithComputerCreateView(LoginRequiredMixin, CreateView):
|
||||||
model = LicenseWithComputer
|
model = LicenseWithComputer
|
||||||
template_name = "licenses/license_with_computer_create.html"
|
template_name = "licenses/license_with_computer_create.html"
|
||||||
fields = "__all__"
|
fields = "__all__" # type: ignore
|
||||||
|
|
||||||
def get_success_url(self):
|
def get_success_url(self):
|
||||||
return reverse("computer", args=(self.computer.pk,))
|
return reverse("computer", args=(self.computer.pk,))
|
||||||
|
@ -57,7 +57,7 @@ class LicenseWithComputerCreateView(LoginRequiredMixin, CreateView):
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
class LicenseWithComputerDeleteView(LoginRequiredMixin, DeleteView):
|
class LicenseWithComputerDeleteView(LoginRequiredMixin, DeleteView): # type: ignore
|
||||||
model = LicenseWithComputer
|
model = LicenseWithComputer
|
||||||
template_name = "licenses/license_with_computer_confirm_delete.html"
|
template_name = "licenses/license_with_computer_confirm_delete.html"
|
||||||
|
|
||||||
|
@ -65,7 +65,7 @@ class LicenseWithComputerDeleteView(LoginRequiredMixin, DeleteView):
|
||||||
return reverse("computer", args=(self.object.computer.pk,))
|
return reverse("computer", args=(self.object.computer.pk,))
|
||||||
|
|
||||||
|
|
||||||
class UserLicenseDeleteView(LoginRequiredMixin, DeleteView):
|
class UserLicenseDeleteView(LoginRequiredMixin, DeleteView): # type: ignore
|
||||||
model = UserLicense
|
model = UserLicense
|
||||||
template_name = "licenses/license_confirm_delete.html"
|
template_name = "licenses/license_confirm_delete.html"
|
||||||
|
|
||||||
|
@ -73,7 +73,7 @@ class UserLicenseDeleteView(LoginRequiredMixin, DeleteView):
|
||||||
return reverse("licenses", args=(self.object.customer.pk,))
|
return reverse("licenses", args=(self.object.customer.pk,))
|
||||||
|
|
||||||
|
|
||||||
class ComputerLicenseDeleteView(LoginRequiredMixin, DeleteView):
|
class ComputerLicenseDeleteView(LoginRequiredMixin, DeleteView): # type: ignore
|
||||||
model = ComputerLicense
|
model = ComputerLicense
|
||||||
template_name = "licenses/license_confirm_delete.html"
|
template_name = "licenses/license_confirm_delete.html"
|
||||||
|
|
||||||
|
|
|
@ -3,9 +3,7 @@ import os
|
||||||
import sys
|
import sys
|
||||||
|
|
||||||
if __name__ == "__main__":
|
if __name__ == "__main__":
|
||||||
os.environ.setdefault(
|
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "network_inventory.settings")
|
||||||
"DJANGO_SETTINGS_MODULE", "network_inventory.settings"
|
|
||||||
)
|
|
||||||
try:
|
try:
|
||||||
from django.core.management import execute_from_command_line
|
from django.core.management import execute_from_command_line
|
||||||
except ImportError as exc:
|
except ImportError as exc:
|
||||||
|
|
|
@ -11,8 +11,6 @@ def net_view_permission(old_fuction):
|
||||||
if user.has_perm("customers.view_customer", net.customer):
|
if user.has_perm("customers.view_customer", net.customer):
|
||||||
return old_fuction(request, pk)
|
return old_fuction(request, pk)
|
||||||
else:
|
else:
|
||||||
return HttpResponseForbidden(
|
return HttpResponseForbidden("You're not allowed to access this device.")
|
||||||
"You're not allowed to access this device."
|
|
||||||
)
|
|
||||||
|
|
||||||
return new_function
|
return new_function
|
||||||
|
|
|
@ -15,9 +15,7 @@ def test_net_detail_view_no_permission(create_admin_user):
|
||||||
net = mixer.blend("nets.Net")
|
net = mixer.blend("nets.Net")
|
||||||
customer = mixer.blend("customers.Customer")
|
customer = mixer.blend("customers.Customer")
|
||||||
device = mixer.blend("computers.Computer", customer=customer)
|
device = mixer.blend("computers.Computer", customer=customer)
|
||||||
mixer.blend(
|
mixer.blend("devices.DeviceInNet", device=device, net=net, ip="10.7.89.101")
|
||||||
"devices.DeviceInNet", device=device, net=net, ip="10.7.89.101"
|
|
||||||
)
|
|
||||||
client = Client()
|
client = Client()
|
||||||
client.login(username="pharma-admin", password="password")
|
client.login(username="pharma-admin", password="password")
|
||||||
response = client.get("/net/" + str(net.id) + "/")
|
response = client.get("/net/" + str(net.id) + "/")
|
||||||
|
@ -28,9 +26,7 @@ def test_net_detail_view(create_admin_user):
|
||||||
fixture = create_admin_user()
|
fixture = create_admin_user()
|
||||||
net = mixer.blend("nets.Net", customer=mixer.SELECT)
|
net = mixer.blend("nets.Net", customer=mixer.SELECT)
|
||||||
device = mixer.blend("computers.Computer", customer=fixture["customer"])
|
device = mixer.blend("computers.Computer", customer=fixture["customer"])
|
||||||
device_in_net = DeviceInNet.objects.create(
|
device_in_net = DeviceInNet.objects.create(device=device, net=net, ip="10.7.89.101")
|
||||||
device=device, net=net, ip="10.7.89.101"
|
|
||||||
)
|
|
||||||
client = Client()
|
client = Client()
|
||||||
client.login(username="pharma-admin", password="password")
|
client.login(username="pharma-admin", password="password")
|
||||||
response = client.get("/net/" + str(net.id) + "/")
|
response = client.get("/net/" + str(net.id) + "/")
|
||||||
|
|
|
@ -29,12 +29,10 @@ def net_detail_view(request, pk):
|
||||||
net = get_object_or_404(Net, pk=pk)
|
net = get_object_or_404(Net, pk=pk)
|
||||||
table = NetDetailTable(DeviceInNet.objects.filter(net=net))
|
table = NetDetailTable(DeviceInNet.objects.filter(net=net))
|
||||||
RequestConfig(request).configure(table)
|
RequestConfig(request).configure(table)
|
||||||
return render(
|
return render(request, "nets/net_details.html", {"table": table, "net": net})
|
||||||
request, "nets/net_details.html", {"table": table, "net": net}
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
class NetDeleteView(LoginRequiredMixin, DeleteView):
|
class NetDeleteView(LoginRequiredMixin, DeleteView): # type: ignore
|
||||||
model = Net
|
model = Net
|
||||||
|
|
||||||
def get_success_url(self):
|
def get_success_url(self):
|
||||||
|
|
|
@ -11,8 +11,6 @@ def user_view_permission(old_fuction):
|
||||||
if user.has_perm("customers.view_customer", inventory_user.customer):
|
if user.has_perm("customers.view_customer", inventory_user.customer):
|
||||||
return old_fuction(request, pk)
|
return old_fuction(request, pk)
|
||||||
else:
|
else:
|
||||||
return HttpResponseForbidden(
|
return HttpResponseForbidden("You're not allowed to access this device.")
|
||||||
"You're not allowed to access this device."
|
|
||||||
)
|
|
||||||
|
|
||||||
return new_function
|
return new_function
|
||||||
|
|
|
@ -37,9 +37,7 @@ def test_customer_user_table_no_user(create_admin_user):
|
||||||
client = Client()
|
client = Client()
|
||||||
client.login(username="pharma-admin", password="password")
|
client.login(username="pharma-admin", password="password")
|
||||||
response = client.get("/customer/" + str(customer.id) + "/users/")
|
response = client.get("/customer/" + str(customer.id) + "/users/")
|
||||||
assert response.status_code == 200 and helper.not_in_content(
|
assert response.status_code == 200 and helper.not_in_content(response, customer)
|
||||||
response, customer
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def test_customer_user_table_no_permission(create_admin_user):
|
def test_customer_user_table_no_permission(create_admin_user):
|
||||||
|
|
|
@ -61,6 +61,4 @@ def test_group_detail_view_with_child_group(create_admin_user):
|
||||||
client = Client()
|
client = Client()
|
||||||
client.login(username="pharma-admin", password="password")
|
client.login(username="pharma-admin", password="password")
|
||||||
response = client.get("/group/" + str(group.id) + "/")
|
response = client.get("/group/" + str(group.id) + "/")
|
||||||
assert response.status_code == 200 and helper.in_content(
|
assert response.status_code == 200 and helper.in_content(response, child_group)
|
||||||
response, child_group
|
|
||||||
)
|
|
||||||
|
|
|
@ -38,9 +38,7 @@ def test_user_detail_view_group(create_admin_user):
|
||||||
client = Client()
|
client = Client()
|
||||||
client.login(username="pharma-admin", password="password")
|
client.login(username="pharma-admin", password="password")
|
||||||
response = client.get("/user/" + str(user.id) + "/")
|
response = client.get("/user/" + str(user.id) + "/")
|
||||||
assert response.status_code == 200 and helper.in_content(
|
assert response.status_code == 200 and helper.in_content(response, "Groups")
|
||||||
response, "Groups"
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def test_user_detail_view_mail_alias(create_admin_user):
|
def test_user_detail_view_mail_alias(create_admin_user):
|
||||||
|
@ -50,9 +48,7 @@ def test_user_detail_view_mail_alias(create_admin_user):
|
||||||
client = Client()
|
client = Client()
|
||||||
client.login(username="pharma-admin", password="password")
|
client.login(username="pharma-admin", password="password")
|
||||||
response = client.get("/user/" + str(user.id) + "/")
|
response = client.get("/user/" + str(user.id) + "/")
|
||||||
assert response.status_code == 200 and helper.in_content(
|
assert response.status_code == 200 and helper.in_content(response, "Mail Alias")
|
||||||
response, "Mail Alias"
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def test_user_detail_view_license(create_admin_user):
|
def test_user_detail_view_license(create_admin_user):
|
||||||
|
@ -63,9 +59,7 @@ def test_user_detail_view_license(create_admin_user):
|
||||||
client = Client()
|
client = Client()
|
||||||
client.login(username="pharma-admin", password="password")
|
client.login(username="pharma-admin", password="password")
|
||||||
response = client.get("/user/" + str(user.id) + "/")
|
response = client.get("/user/" + str(user.id) + "/")
|
||||||
assert response.status_code == 200 and helper.in_content(
|
assert response.status_code == 200 and helper.in_content(response, "License")
|
||||||
response, "License"
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def test_user_detail_view_computer(create_admin_user):
|
def test_user_detail_view_computer(create_admin_user):
|
||||||
|
@ -75,9 +69,7 @@ def test_user_detail_view_computer(create_admin_user):
|
||||||
client = Client()
|
client = Client()
|
||||||
client.login(username="pharma-admin", password="password")
|
client.login(username="pharma-admin", password="password")
|
||||||
response = client.get("/user/" + str(user.id) + "/")
|
response = client.get("/user/" + str(user.id) + "/")
|
||||||
assert response.status_code == 200 and helper.in_content(
|
assert response.status_code == 200 and helper.in_content(response, computer)
|
||||||
response, computer
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def test_user_detail_view_no_permission(create_admin_user):
|
def test_user_detail_view_no_permission(create_admin_user):
|
||||||
|
|
|
@ -52,7 +52,7 @@ def user_detail_view(request, pk):
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
class UserDeleteView(LoginRequiredMixin, DeleteView):
|
class UserDeleteView(LoginRequiredMixin, DeleteView): # type: ignore
|
||||||
model = User
|
model = User
|
||||||
|
|
||||||
def get_success_url(self):
|
def get_success_url(self):
|
||||||
|
@ -64,9 +64,7 @@ class UserDeleteView(LoginRequiredMixin, DeleteView):
|
||||||
def groups_table_view(request, pk):
|
def groups_table_view(request, pk):
|
||||||
customer = get_object_or_404(Customer, pk=pk)
|
customer = get_object_or_404(Customer, pk=pk)
|
||||||
groups_table = GroupsTable(
|
groups_table = GroupsTable(
|
||||||
utils.get_objects_for_customer(
|
utils.get_objects_for_customer(Group, user=request.user, customer_pk=pk)
|
||||||
Group, user=request.user, customer_pk=pk
|
|
||||||
)
|
|
||||||
)
|
)
|
||||||
RequestConfig(request).configure(groups_table)
|
RequestConfig(request).configure(groups_table)
|
||||||
return TemplateResponse(
|
return TemplateResponse(
|
||||||
|
@ -81,9 +79,7 @@ def groups_table_view(request, pk):
|
||||||
|
|
||||||
@login_required
|
@login_required
|
||||||
def group_detail_view(request, pk):
|
def group_detail_view(request, pk):
|
||||||
group = utils.get_object_with_view_permission(
|
group = utils.get_object_with_view_permission(Group, user=request.user, pk=pk)
|
||||||
Group, user=request.user, pk=pk
|
|
||||||
)
|
|
||||||
users = group.user_set.all()
|
users = group.user_set.all()
|
||||||
groups = Group.objects.filter(parent_group=group)
|
groups = Group.objects.filter(parent_group=group)
|
||||||
print(groups)
|
print(groups)
|
||||||
|
@ -96,9 +92,7 @@ def group_detail_view(request, pk):
|
||||||
|
|
||||||
@login_required
|
@login_required
|
||||||
def delete_group(request, pk):
|
def delete_group(request, pk):
|
||||||
group = utils.get_object_with_view_permission(
|
group = utils.get_object_with_view_permission(Group, user=request.user, pk=pk)
|
||||||
Group, user=request.user, pk=pk
|
|
||||||
)
|
|
||||||
if request.method == "POST":
|
if request.method == "POST":
|
||||||
group.delete()
|
group.delete()
|
||||||
return redirect("groups", pk=group.customer.pk)
|
return redirect("groups", pk=group.customer.pk)
|
||||||
|
|
Loading…
Reference in New Issue