mirror of
https://github.com/YunoHost-Apps/pyinventory_ynh.git
synced 2024-09-03 20:16:09 +02:00
commit
3ffba4eb9a
23 changed files with 488 additions and 638 deletions
25
README.md
25
README.md
|
@ -24,10 +24,6 @@ If you don't have YunoHost, please consult [the guide](https://yunohost.org/#/in
|
||||||
|
|
||||||
[PyInventory](https://github.com/jedie/PyInventory) is a libre web-based management to catalog things including state and location etc. using [Python](https://www.python.org/)/[Django](https://www.djangoproject.com/).
|
[PyInventory](https://github.com/jedie/PyInventory) is a libre web-based management to catalog things including state and location etc. using [Python](https://www.python.org/)/[Django](https://www.djangoproject.com/).
|
||||||
|
|
||||||
[![Integration level](https://dash.yunohost.org/integration/pyinventory_ynh.svg)](https://dash.yunohost.org/appci/app/pyinventory_ynh) ![](https://ci-apps.yunohost.org/ci/badges/pyinventory_ynh.status.svg) ![](https://ci-apps.yunohost.org/ci/badges/pyinventory_ynh.maintain.svg)
|
|
||||||
[![Install pyinventory_ynh with YunoHost](https://install-app.yunohost.org/install-with-yunohost.svg)](https://install-app.yunohost.org/?app=pyinventory_ynh)
|
|
||||||
|
|
||||||
|
|
||||||
Pull requests welcome ;)
|
Pull requests welcome ;)
|
||||||
|
|
||||||
This package for YunoHost used [django-yunohost-integration](https://github.com/YunoHost-Apps/django_yunohost_integration)
|
This package for YunoHost used [django-yunohost-integration](https://github.com/YunoHost-Apps/django_yunohost_integration)
|
||||||
|
@ -35,7 +31,7 @@ This package for YunoHost used [django-yunohost-integration](https://github.com/
|
||||||
More screenshots are here: jedie.github.io/tree/master/screenshots/PyInventory
|
More screenshots are here: jedie.github.io/tree/master/screenshots/PyInventory
|
||||||
|
|
||||||
|
|
||||||
**Shipped version:** 0.19.3~ynh1
|
**Shipped version:** 0.19.3~ynh2
|
||||||
|
|
||||||
## Screenshots
|
## Screenshots
|
||||||
|
|
||||||
|
@ -44,27 +40,8 @@ More screenshots are here: jedie.github.io/tree/master/screenshots/PyInventory
|
||||||
![Screenshot of PyInventory](./doc/screenshots/pyinventory_v020_screenshot_1.png)
|
![Screenshot of PyInventory](./doc/screenshots/pyinventory_v020_screenshot_1.png)
|
||||||
![Screenshot of PyInventory](./doc/screenshots/pyinventory_v0110_screenshot_memo_1.png)
|
![Screenshot of PyInventory](./doc/screenshots/pyinventory_v0110_screenshot_memo_1.png)
|
||||||
|
|
||||||
## Disclaimers / important information
|
|
||||||
|
|
||||||
## Settings and upgrades
|
|
||||||
|
|
||||||
Almost everything related to PyInventory's configuration is handled in a `"../conf/settings.py"` file.
|
|
||||||
You can edit the file `/home/yunohost.app/django_example/local_settings.py` to enable or disable features.
|
|
||||||
|
|
||||||
Test sending emails, e.g.:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
ssh admin@yourdomain.tld
|
|
||||||
root@yunohost:~# /home/yunohost.app/pyinventory/manage.py sendtestemail --admins
|
|
||||||
```
|
|
||||||
|
|
||||||
How to debug a django YunoHost app, take a look into:
|
|
||||||
|
|
||||||
* https://github.com/YunoHost-Apps/django_example_ynh#developer-info
|
|
||||||
|
|
||||||
## Documentation and resources
|
## Documentation and resources
|
||||||
|
|
||||||
* Official app website: <https://github.com/YunoHost-Apps/pyinventory_ynh>
|
|
||||||
* Official user documentation: <https://github.com/jedie/PyInventory>
|
* Official user documentation: <https://github.com/jedie/PyInventory>
|
||||||
* Official admin documentation: <https://github.com/YunoHost-Apps/pyinventory_ynh>
|
* Official admin documentation: <https://github.com/YunoHost-Apps/pyinventory_ynh>
|
||||||
* Upstream app code repository: <https://github.com/YunoHost-Apps/pyinventory_ynh>
|
* Upstream app code repository: <https://github.com/YunoHost-Apps/pyinventory_ynh>
|
||||||
|
|
25
README_fr.md
25
README_fr.md
|
@ -24,10 +24,6 @@ Si vous n’avez pas YunoHost, regardez [ici](https://yunohost.org/#/install) po
|
||||||
|
|
||||||
[PyInventory](https://github.com/jedie/PyInventory) is a libre web-based management to catalog things including state and location etc. using [Python](https://www.python.org/)/[Django](https://www.djangoproject.com/).
|
[PyInventory](https://github.com/jedie/PyInventory) is a libre web-based management to catalog things including state and location etc. using [Python](https://www.python.org/)/[Django](https://www.djangoproject.com/).
|
||||||
|
|
||||||
[![Integration level](https://dash.yunohost.org/integration/pyinventory_ynh.svg)](https://dash.yunohost.org/appci/app/pyinventory_ynh) ![](https://ci-apps.yunohost.org/ci/badges/pyinventory_ynh.status.svg) ![](https://ci-apps.yunohost.org/ci/badges/pyinventory_ynh.maintain.svg)
|
|
||||||
[![Install pyinventory_ynh with YunoHost](https://install-app.yunohost.org/install-with-yunohost.svg)](https://install-app.yunohost.org/?app=pyinventory_ynh)
|
|
||||||
|
|
||||||
|
|
||||||
Pull requests welcome ;)
|
Pull requests welcome ;)
|
||||||
|
|
||||||
This package for YunoHost used [django-yunohost-integration](https://github.com/YunoHost-Apps/django_yunohost_integration)
|
This package for YunoHost used [django-yunohost-integration](https://github.com/YunoHost-Apps/django_yunohost_integration)
|
||||||
|
@ -35,7 +31,7 @@ This package for YunoHost used [django-yunohost-integration](https://github.com/
|
||||||
More screenshots are here: jedie.github.io/tree/master/screenshots/PyInventory
|
More screenshots are here: jedie.github.io/tree/master/screenshots/PyInventory
|
||||||
|
|
||||||
|
|
||||||
**Version incluse :** 0.19.3~ynh1
|
**Version incluse :** 0.19.3~ynh2
|
||||||
|
|
||||||
## Captures d’écran
|
## Captures d’écran
|
||||||
|
|
||||||
|
@ -44,27 +40,8 @@ More screenshots are here: jedie.github.io/tree/master/screenshots/PyInventory
|
||||||
![Capture d’écran de PyInventory](./doc/screenshots/pyinventory_v020_screenshot_1.png)
|
![Capture d’écran de PyInventory](./doc/screenshots/pyinventory_v020_screenshot_1.png)
|
||||||
![Capture d’écran de PyInventory](./doc/screenshots/pyinventory_v0110_screenshot_memo_1.png)
|
![Capture d’écran de PyInventory](./doc/screenshots/pyinventory_v0110_screenshot_memo_1.png)
|
||||||
|
|
||||||
## Avertissements / informations importantes
|
|
||||||
|
|
||||||
## Settings and upgrades
|
|
||||||
|
|
||||||
Almost everything related to PyInventory's configuration is handled in a `"../conf/settings.py"` file.
|
|
||||||
You can edit the file `/home/yunohost.app/django_example/local_settings.py` to enable or disable features.
|
|
||||||
|
|
||||||
Test sending emails, e.g.:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
ssh admin@yourdomain.tld
|
|
||||||
root@yunohost:~# /home/yunohost.app/pyinventory/manage.py sendtestemail --admins
|
|
||||||
```
|
|
||||||
|
|
||||||
How to debug a django YunoHost app, take a look into:
|
|
||||||
|
|
||||||
* https://github.com/YunoHost-Apps/django_example_ynh#developer-info
|
|
||||||
|
|
||||||
## Documentations et ressources
|
## Documentations et ressources
|
||||||
|
|
||||||
* Site officiel de l’app : <https://github.com/YunoHost-Apps/pyinventory_ynh>
|
|
||||||
* Documentation officielle utilisateur : <https://github.com/jedie/PyInventory>
|
* Documentation officielle utilisateur : <https://github.com/jedie/PyInventory>
|
||||||
* Documentation officielle de l’admin : <https://github.com/YunoHost-Apps/pyinventory_ynh>
|
* Documentation officielle de l’admin : <https://github.com/YunoHost-Apps/pyinventory_ynh>
|
||||||
* Dépôt de code officiel de l’app : <https://github.com/YunoHost-Apps/pyinventory_ynh>
|
* Dépôt de code officiel de l’app : <https://github.com/YunoHost-Apps/pyinventory_ynh>
|
||||||
|
|
|
@ -16,9 +16,9 @@ bleach==6.1.0 \
|
||||||
--hash=sha256:0a31f1837963c41d46bbf1331b8778e1308ea0791db03cc4e7357b97cf42a8fe \
|
--hash=sha256:0a31f1837963c41d46bbf1331b8778e1308ea0791db03cc4e7357b97cf42a8fe \
|
||||||
--hash=sha256:3225f354cfc436b9789c66c4ee030194bee0568fbf9cbdad3bc8b5c26c5f12b6
|
--hash=sha256:3225f354cfc436b9789c66c4ee030194bee0568fbf9cbdad3bc8b5c26c5f12b6
|
||||||
# via django-tools
|
# via django-tools
|
||||||
bx-django-utils==67 \
|
bx-django-utils==69 \
|
||||||
--hash=sha256:8740fdaf98ed68a8ddb3af025d9b4f87c99101405898ddca86810b0c384b215a \
|
--hash=sha256:39e96b8ad47bcf36d6713e4e42c8d09deb21e413160dc2944f17b7d2e2244713 \
|
||||||
--hash=sha256:aca0ae5c91a62e4f594172b8c43468c701516f99ae50d99412d5299ba375df03
|
--hash=sha256:59b806aa36b50184f14bd0f7a61fb66c478fa231a44f92472360ce0cf1616013
|
||||||
# via pyinventory
|
# via pyinventory
|
||||||
bx-py-utils==88 \
|
bx-py-utils==88 \
|
||||||
--hash=sha256:32fbc7e9ff3dfb0a817c80fb1d165ec559643dab59c0be549e646acbf8223b75 \
|
--hash=sha256:32fbc7e9ff3dfb0a817c80fb1d165ec559643dab59c0be549e646acbf8223b75 \
|
||||||
|
@ -28,9 +28,9 @@ bx-py-utils==88 \
|
||||||
# cli-base-utilities
|
# cli-base-utilities
|
||||||
# django-tools
|
# django-tools
|
||||||
# pyinventory
|
# pyinventory
|
||||||
certifi==2023.7.22 \
|
certifi==2023.11.17 \
|
||||||
--hash=sha256:539cc1d13202e33ca466e88b2807e29f4c13049d6d87031a3c110744495cb082 \
|
--hash=sha256:9b469f3a900bf28dc19b8cfbf8019bf47f7fdd1a65a1d4ffb98fc14166beb4d1 \
|
||||||
--hash=sha256:92d6037539857d8206b8f6ae472e8b77db8058fec5937a1ef3f54304089edbb9
|
--hash=sha256:e036ab49d5b79556f99cfc2d9320b34cfbe5be05c5871b51de9329f0603b0474
|
||||||
# via requests
|
# via requests
|
||||||
charset-normalizer==3.3.2 \
|
charset-normalizer==3.3.2 \
|
||||||
--hash=sha256:06435b539f889b1f6f4ac1758871aae42dc3a8c0e24ac9e60c2384973ad73027 \
|
--hash=sha256:06435b539f889b1f6f4ac1758871aae42dc3a8c0e24ac9e60c2384973ad73027 \
|
||||||
|
@ -189,9 +189,9 @@ django-debug-toolbar==4.2.0 \
|
||||||
--hash=sha256:af99128c06e8e794479e65ab62cc6c7d1e74e1c19beb44dcbf9bad7a9c017327 \
|
--hash=sha256:af99128c06e8e794479e65ab62cc6c7d1e74e1c19beb44dcbf9bad7a9c017327 \
|
||||||
--hash=sha256:bc7fdaafafcdedefcc67a4a5ad9dac96efd6e41db15bc74d402a54a2ba4854dc
|
--hash=sha256:bc7fdaafafcdedefcc67a4a5ad9dac96efd6e41db15bc74d402a54a2ba4854dc
|
||||||
# via pyinventory
|
# via pyinventory
|
||||||
django-import-export==3.3.2 \
|
django-import-export==3.3.3 \
|
||||||
--hash=sha256:9a5c7c191014e4defb01573ee94864b60724a203f1b8a7e5e67a03f06b27b62d \
|
--hash=sha256:2c1b16e1cf2ea5f62a165d8867e7c6dcff25673ab7201fd18aaf67c9ee90367e \
|
||||||
--hash=sha256:d13e7508190f46442280bd7d04efcf49af6521350a70a6f9e06447ef28d6a41d
|
--hash=sha256:78973202e93897326ab0411d64eaf89b72779fcb21ee9e5f64f3fb96571a5978
|
||||||
# via pyinventory
|
# via pyinventory
|
||||||
django-js-asset==2.1.0 \
|
django-js-asset==2.1.0 \
|
||||||
--hash=sha256:36a3a4dd6e9efc895fb127d13126020f6ec1ec9469ad42878d42143f22495d90 \
|
--hash=sha256:36a3a4dd6e9efc895fb127d13126020f6ec1ec9469ad42878d42143f22495d90 \
|
||||||
|
@ -239,9 +239,9 @@ icdiff==2.0.7 \
|
||||||
--hash=sha256:f05d1b3623223dd1c70f7848da7d699de3d9a2550b902a8234d9026292fb5762 \
|
--hash=sha256:f05d1b3623223dd1c70f7848da7d699de3d9a2550b902a8234d9026292fb5762 \
|
||||||
--hash=sha256:f79a318891adbf59a45e3a7694f5e1f18c5407065264637072ac8363b759866f
|
--hash=sha256:f79a318891adbf59a45e3a7694f5e1f18c5407065264637072ac8363b759866f
|
||||||
# via django-tools
|
# via django-tools
|
||||||
idna==3.4 \
|
idna==3.6 \
|
||||||
--hash=sha256:814f528e8dead7d329833b91c5faa87d60bf71824cd12a7530b5526063d02cb4 \
|
--hash=sha256:9ecdbbd083b06798ae1e86adcbfe8ab1479cf864e4ee30fe4e46a003d12491ca \
|
||||||
--hash=sha256:90b77e79eaa3eba6de819a0c442c0b4ceefc341a7a2ab77d7562bf49f425c5c2
|
--hash=sha256:c05567e9c24a6b9faaa835c4821bad0590fbb9d5779e7caa6e1cc4978e7eb24f
|
||||||
# via requests
|
# via requests
|
||||||
markdown-it-py==3.0.0 \
|
markdown-it-py==3.0.0 \
|
||||||
--hash=sha256:355216845c60bd96232cd8d8c40e8f9765cc86f46880e43a8fd22dc1a1a8cab1 \
|
--hash=sha256:355216845c60bd96232cd8d8c40e8f9765cc86f46880e43a8fd22dc1a1a8cab1 \
|
||||||
|
@ -342,9 +342,9 @@ psycopg2==2.9.9 \
|
||||||
--hash=sha256:de80739447af31525feddeb8effd640782cf5998e1a4e9192ebdf829717e3913 \
|
--hash=sha256:de80739447af31525feddeb8effd640782cf5998e1a4e9192ebdf829717e3913 \
|
||||||
--hash=sha256:ff432630e510709564c01dafdbe996cb552e0b9f3f065eb89bdce5bd31fabf4c
|
--hash=sha256:ff432630e510709564c01dafdbe996cb552e0b9f3f065eb89bdce5bd31fabf4c
|
||||||
# via django-yunohost-integration
|
# via django-yunohost-integration
|
||||||
pygments==2.16.1 \
|
pygments==2.17.2 \
|
||||||
--hash=sha256:13fc09fa63bc8d8671a6d247e1eb303c4b343eaee81d861f3404db2935653692 \
|
--hash=sha256:b27c2826c47d0f3219f29554824c30c5e8945175d888647acd804ddd04af846c \
|
||||||
--hash=sha256:1daff0494820c69bc8941e407aa20f577374ee88364ee10a98fdbe0aece96e29
|
--hash=sha256:da46cec9fd2de5be3a8a784f434e4c4ab670b4ff54d605c4c2717e9d49c4c367
|
||||||
# via rich
|
# via rich
|
||||||
pyinventory==0.19.3 \
|
pyinventory==0.19.3 \
|
||||||
--hash=sha256:42e5710956e466df389ddf01c1ab8f9c432890b745a2a32765085c67fda78cfa \
|
--hash=sha256:42e5710956e466df389ddf01c1ab8f9c432890b745a2a32765085c67fda78cfa \
|
||||||
|
@ -420,9 +420,9 @@ requests==2.31.0 \
|
||||||
--hash=sha256:58cd2187c01e70e6e26505bca751777aa9f2ee0b7f4300988b709f44e013003f \
|
--hash=sha256:58cd2187c01e70e6e26505bca751777aa9f2ee0b7f4300988b709f44e013003f \
|
||||||
--hash=sha256:942c5a758f98d790eaed1a29cb6eefc7ffb0d1cf7af05c3d2791656dbd6ad1e1
|
--hash=sha256:942c5a758f98d790eaed1a29cb6eefc7ffb0d1cf7af05c3d2791656dbd6ad1e1
|
||||||
# via pyinventory
|
# via pyinventory
|
||||||
rich==13.6.0 \
|
rich==13.7.0 \
|
||||||
--hash=sha256:2b38e2fe9ca72c9a00170a1a2d20c63c790d0e10ef1fe35eba76e1e7b1d7d245 \
|
--hash=sha256:5cb5123b5cf9ee70584244246816e9114227e0b98ad9176eede6ad54bf5403fa \
|
||||||
--hash=sha256:5c14d22737e6d5084ef4771b62d5d4363165b403455a30a1c8ca39dc7b644bef
|
--hash=sha256:6da14c108c4866ee9520bbffa71f6fe3962e193b7da68720583850cd4548e235
|
||||||
# via
|
# via
|
||||||
# cli-base-utilities
|
# cli-base-utilities
|
||||||
# rich-click
|
# rich-click
|
||||||
|
@ -446,17 +446,17 @@ tablib[html,ods,xls,xlsx,yaml]==3.5.0 \
|
||||||
# via
|
# via
|
||||||
# django-import-export
|
# django-import-export
|
||||||
# tablib
|
# tablib
|
||||||
tomlkit==0.12.2 \
|
tomlkit==0.12.3 \
|
||||||
--hash=sha256:df32fab589a81f0d7dc525a4267b6d7a64ee99619cbd1eeb0fae32c1dd426977 \
|
--hash=sha256:75baf5012d06501f07bee5bf8e801b9f343e7aac5a92581f20f80ce632e6b5a4 \
|
||||||
--hash=sha256:eeea7ac7563faeab0a1ed8fe12c2e5a51c61f933f2502f7e9db0241a65163ad0
|
--hash=sha256:b0a645a9156dc7cb5d3a1f0d4bab66db287fcb8e0430bdd4664a095ea16414ba
|
||||||
# via cli-base-utilities
|
# via cli-base-utilities
|
||||||
typing-extensions==4.8.0 \
|
typing-extensions==4.8.0 \
|
||||||
--hash=sha256:8f92fc8806f9a6b641eaa5318da32b44d401efaac0f6678c9bc448ba3605faa0 \
|
--hash=sha256:8f92fc8806f9a6b641eaa5318da32b44d401efaac0f6678c9bc448ba3605faa0 \
|
||||||
--hash=sha256:df8e4339e9cb77357558cbdbceca33c303714cf861d1eef15e1070055ae8b7ef
|
--hash=sha256:df8e4339e9cb77357558cbdbceca33c303714cf861d1eef15e1070055ae8b7ef
|
||||||
# via rich-click
|
# via rich-click
|
||||||
urllib3==2.0.7 \
|
urllib3==2.1.0 \
|
||||||
--hash=sha256:c97dfde1f7bd43a71c8d2a58e369e9b2bf692d1334ea9f9cae55add7d0dd0f84 \
|
--hash=sha256:55901e917a5896a349ff771be919f8bd99aff50b79fe58fec595eb37bbc56bb3 \
|
||||||
--hash=sha256:fdb6d215c776278489906c2f8916e6e7d4f5a9b602ccbcfdf7f016fc8da0596e
|
--hash=sha256:df7aa8afb0148fa78488e7899b2c59b5f4ffcfa82e6c54ccb9dd37c1d7b52d54
|
||||||
# via requests
|
# via requests
|
||||||
webencodings==0.5.1 \
|
webencodings==0.5.1 \
|
||||||
--hash=sha256:a0af1213f3c2226497a97e2b3aa01a7e4bee4f403f95be16fc9acd2947514a78 \
|
--hash=sha256:a0af1213f3c2226497a97e2b3aa01a7e4bee4f403f95be16fc9acd2947514a78 \
|
||||||
|
@ -472,7 +472,7 @@ xlwt==1.3.0 \
|
||||||
# via tablib
|
# via tablib
|
||||||
|
|
||||||
# The following packages are considered to be unsafe in a requirements file:
|
# The following packages are considered to be unsafe in a requirements file:
|
||||||
setuptools==68.2.2 \
|
setuptools==69.0.2 \
|
||||||
--hash=sha256:4ac1475276d2f1c48684874089fefcd83bd7162ddaafb81fac866ba0db282a87 \
|
--hash=sha256:1e8fdff6797d3865f37397be788a4e3cba233608e9b509382a2777d25ebde7f2 \
|
||||||
--hash=sha256:b454a35605876da60632df1a60f736524eb73cc47bbc9f3f1ef1b644de74fd2a
|
--hash=sha256:735896e78a4742605974de002ac60562d286fa8051a7e2299445e8e8fbb01aa6
|
||||||
# via django-axes
|
# via django-axes
|
||||||
|
|
|
@ -40,7 +40,7 @@ YNH_CURRENT_HOST = '__YNH_CURRENT_HOST__' # YunoHost main domain from: /etc/yun
|
||||||
# config_panel.toml settings:
|
# config_panel.toml settings:
|
||||||
|
|
||||||
DEBUG_ENABLED = '__DEBUG_ENABLED__'
|
DEBUG_ENABLED = '__DEBUG_ENABLED__'
|
||||||
DEBUG = DEBUG_ENABLED == 'YES'
|
DEBUG = DEBUG_ENABLED == '1'
|
||||||
|
|
||||||
LOG_LEVEL = '__LOG_LEVEL__'
|
LOG_LEVEL = '__LOG_LEVEL__'
|
||||||
ADMIN_EMAIL = '__ADMIN_EMAIL__'
|
ADMIN_EMAIL = '__ADMIN_EMAIL__'
|
||||||
|
|
|
@ -1,8 +1,14 @@
|
||||||
|
from inventory.permissions import get_or_create_normal_user_group
|
||||||
|
|
||||||
|
|
||||||
def setup_project_user(user):
|
def setup_project_user(user):
|
||||||
"""
|
"""
|
||||||
All users used the Django admin, so we need to set the "staff" user flag.
|
All users used the Django admin, so we need to set the "staff" user flag.
|
||||||
Called from django_yunohost_integration.sso_auth
|
Called from django_yunohost_integration.sso_auth
|
||||||
"""
|
"""
|
||||||
|
pyinventory_user_group = get_or_create_normal_user_group()[0]
|
||||||
|
user.groups.set([pyinventory_user_group])
|
||||||
|
|
||||||
user.is_staff = True
|
user.is_staff = True
|
||||||
user.save()
|
user.save()
|
||||||
return user
|
return user
|
||||||
|
|
60
doc/ADMIN.md
Normal file
60
doc/ADMIN.md
Normal file
|
@ -0,0 +1,60 @@
|
||||||
|
## Settings and upgrades
|
||||||
|
|
||||||
|
Almost everything related to PyInventory's configuration is handled in a `"../conf/settings.py"` file.
|
||||||
|
You can edit the file `/home/yunohost.app/django_example/local_settings.py` to enable or disable features.
|
||||||
|
|
||||||
|
Test sending emails, e.g.:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
ssh admin@yourdomain.tld
|
||||||
|
root@yunohost:~# /home/yunohost.app/pyinventory/manage.py sendtestemail --admins
|
||||||
|
```
|
||||||
|
|
||||||
|
How to debug a django YunoHost app, take a look into:
|
||||||
|
|
||||||
|
* https://github.com/YunoHost-Apps/django_example_ynh#developer-info
|
||||||
|
|
||||||
|
## local test
|
||||||
|
|
||||||
|
For quicker developing of pyinventory_ynh in the context of YunoHost app,
|
||||||
|
it's possible to run the Django developer server with the settings
|
||||||
|
and urls made for YunoHost installation.
|
||||||
|
|
||||||
|
e.g.:
|
||||||
|
```bash
|
||||||
|
~$ git clone https://github.com/YunoHost-Apps/django_example.git
|
||||||
|
~$ cd pyinventory_ynh/
|
||||||
|
~/django_example$ ./dev-cli.py --help
|
||||||
|
```
|
||||||
|
|
||||||
|
|
||||||
|
The output will looks like:
|
||||||
|
|
||||||
|
[comment]: <> (✂✂✂ auto generated help start ✂✂✂)
|
||||||
|
```
|
||||||
|
Usage: ./dev-cli.py [OPTIONS] COMMAND [ARGS]...
|
||||||
|
|
||||||
|
╭─ Options ────────────────────────────────────────────────────────────────────────────────────────╮
|
||||||
|
│ --help Show this message and exit. │
|
||||||
|
╰──────────────────────────────────────────────────────────────────────────────────────────────────╯
|
||||||
|
╭─ Commands ───────────────────────────────────────────────────────────────────────────────────────╮
|
||||||
|
│ check-code-style Check code style by calling darker + flake8 │
|
||||||
|
│ coverage Run and show coverage. │
|
||||||
|
│ diffsettings Run "diffsettings" manage command against a "local_test" YunoHost │
|
||||||
|
│ installation. │
|
||||||
|
│ fix-code-style Fix code style of all pyinventory_ynh source code files via darker │
|
||||||
|
│ install Run pip-sync and install 'pyinventory_ynh' via pip as editable. │
|
||||||
|
│ local-test Build a "local_test" YunoHost installation and start the Django dev. │
|
||||||
|
│ server against it. │
|
||||||
|
│ mypy Run Mypy (configured in pyproject.toml) │
|
||||||
|
│ publish Build and upload this project to PyPi │
|
||||||
|
│ safety Run safety check against current requirements files │
|
||||||
|
│ test Compile YunoHost files and run Django unittests │
|
||||||
|
│ tox Run tox │
|
||||||
|
│ update Update "requirements*.txt" dependencies files │
|
||||||
|
│ update-test-snapshot-files Update all test snapshot files (by remove and recreate all snapshot │
|
||||||
|
│ files) │
|
||||||
|
│ version Print version and exit │
|
||||||
|
╰──────────────────────────────────────────────────────────────────────────────────────────────────╯
|
||||||
|
```
|
||||||
|
[comment]: <> (✂✂✂ auto generated help end ✂✂✂)
|
|
@ -6,10 +6,6 @@
|
||||||
|
|
||||||
[PyInventory](https://github.com/jedie/PyInventory) is a libre web-based management to catalog things including state and location etc. using [Python](https://www.python.org/)/[Django](https://www.djangoproject.com/).
|
[PyInventory](https://github.com/jedie/PyInventory) is a libre web-based management to catalog things including state and location etc. using [Python](https://www.python.org/)/[Django](https://www.djangoproject.com/).
|
||||||
|
|
||||||
[![Integration level](https://dash.yunohost.org/integration/pyinventory_ynh.svg)](https://dash.yunohost.org/appci/app/pyinventory_ynh) ![](https://ci-apps.yunohost.org/ci/badges/pyinventory_ynh.status.svg) ![](https://ci-apps.yunohost.org/ci/badges/pyinventory_ynh.maintain.svg)
|
|
||||||
[![Install pyinventory_ynh with YunoHost](https://install-app.yunohost.org/install-with-yunohost.svg)](https://install-app.yunohost.org/?app=pyinventory_ynh)
|
|
||||||
|
|
||||||
|
|
||||||
Pull requests welcome ;)
|
Pull requests welcome ;)
|
||||||
|
|
||||||
This package for YunoHost used [django-yunohost-integration](https://github.com/YunoHost-Apps/django_yunohost_integration)
|
This package for YunoHost used [django-yunohost-integration](https://github.com/YunoHost-Apps/django_yunohost_integration)
|
||||||
|
|
|
@ -1,15 +0,0 @@
|
||||||
## Settings and upgrades
|
|
||||||
|
|
||||||
Almost everything related to PyInventory's configuration is handled in a `"../conf/settings.py"` file.
|
|
||||||
You can edit the file `/home/yunohost.app/django_example/local_settings.py` to enable or disable features.
|
|
||||||
|
|
||||||
Test sending emails, e.g.:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
ssh admin@yourdomain.tld
|
|
||||||
root@yunohost:~# /home/yunohost.app/pyinventory/manage.py sendtestemail --admins
|
|
||||||
```
|
|
||||||
|
|
||||||
How to debug a django YunoHost app, take a look into:
|
|
||||||
|
|
||||||
* https://github.com/YunoHost-Apps/django_example_ynh#developer-info
|
|
|
@ -5,7 +5,7 @@ id = "pyinventory"
|
||||||
name = "PyInventory"
|
name = "PyInventory"
|
||||||
description.en = "Web based management to catalog things including state and location etc."
|
description.en = "Web based management to catalog things including state and location etc."
|
||||||
|
|
||||||
version = "0.19.3~ynh1"
|
version = "0.19.3~ynh2"
|
||||||
|
|
||||||
maintainers = ["Jens Diemer"]
|
maintainers = ["Jens Diemer"]
|
||||||
|
|
||||||
|
@ -13,12 +13,12 @@ maintainers = ["Jens Diemer"]
|
||||||
[upstream]
|
[upstream]
|
||||||
# https://yunohost.org/en/packaging_manifest#upstream-section
|
# https://yunohost.org/en/packaging_manifest#upstream-section
|
||||||
license = "GPL-3.0-or-later"
|
license = "GPL-3.0-or-later"
|
||||||
website = "https://github.com/YunoHost-Apps/pyinventory_ynh"
|
|
||||||
admindoc = "https://github.com/YunoHost-Apps/pyinventory_ynh"
|
admindoc = "https://github.com/YunoHost-Apps/pyinventory_ynh"
|
||||||
userdoc = "https://github.com/jedie/PyInventory"
|
userdoc = "https://github.com/jedie/PyInventory"
|
||||||
code = "https://github.com/YunoHost-Apps/pyinventory_ynh"
|
code = "https://github.com/YunoHost-Apps/pyinventory_ynh"
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
[integration]
|
[integration]
|
||||||
# https://yunohost.org/en/packaging_manifest#integration-section
|
# https://yunohost.org/en/packaging_manifest#integration-section
|
||||||
yunohost = ">=11"
|
yunohost = ">=11"
|
||||||
|
@ -31,7 +31,10 @@ ram.build = "50M" # **estimate** minimum ram requirement. e.g. 50M, 400M, 1G, ..
|
||||||
ram.runtime = "50M" # **estimate** minimum ram requirement. e.g. 50M, 400M, 1G, ...
|
ram.runtime = "50M" # **estimate** minimum ram requirement. e.g. 50M, 400M, 1G, ...
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
[install]
|
[install]
|
||||||
|
# https://yunohost.org/en/packaging_manifest#install-questions
|
||||||
|
|
||||||
[install.domain]
|
[install.domain]
|
||||||
# this is a generic question - ask strings are automatically handled by Yunohost's core
|
# this is a generic question - ask strings are automatically handled by Yunohost's core
|
||||||
type = "domain"
|
type = "domain"
|
||||||
|
@ -61,11 +64,9 @@ ram.runtime = "50M" # **estimate** minimum ram requirement. e.g. 50M, 400M, 1G,
|
||||||
type = "email"
|
type = "email"
|
||||||
example = "admin@example.com"
|
example = "admin@example.com"
|
||||||
|
|
||||||
[install.debug_enabled] # __DEBUG_ENABLED__
|
[install.debug_enabled] # __DEBUG_ENABLED__ will be set to "0" or "1" string
|
||||||
ask.en = "Should be never enabled in production!"
|
ask.en = "Should be never enabled in production!"
|
||||||
type = "select"
|
type = "boolean"
|
||||||
choices = ["YES", "NO"]
|
|
||||||
default = "NO"
|
|
||||||
|
|
||||||
[install.log_level] # __LOG_LEVEL__
|
[install.log_level] # __LOG_LEVEL__
|
||||||
ask.en = "Logging level"
|
ask.en = "Logging level"
|
||||||
|
|
|
@ -3,5 +3,5 @@
|
||||||
Web based management to catalog things including state and location etc.
|
Web based management to catalog things including state and location etc.
|
||||||
"""
|
"""
|
||||||
|
|
||||||
__version__ = '0.19.3+ynh1'
|
__version__ = '0.19.3+ynh2'
|
||||||
__author__ = 'Jens Diemer <pyinventory_ynh@jensdiemer.de>'
|
__author__ = 'Jens Diemer <pyinventory_ynh@jensdiemer.de>'
|
||||||
|
|
|
@ -2,14 +2,17 @@
|
||||||
CLI for development
|
CLI for development
|
||||||
"""
|
"""
|
||||||
import logging
|
import logging
|
||||||
|
import os
|
||||||
import sys
|
import sys
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
|
|
||||||
|
import django
|
||||||
import rich_click as click
|
import rich_click as click
|
||||||
from bx_py_utils.path import assert_is_file
|
from bx_py_utils.path import assert_is_file
|
||||||
from cli_base.cli_tools.subprocess_utils import verbose_check_call
|
from cli_base.cli_tools.subprocess_utils import verbose_check_call
|
||||||
from cli_base.cli_tools.version_info import print_version
|
from cli_base.cli_tools.version_info import print_version
|
||||||
from django_yunohost_integration.local_test import create_local_test
|
from django.core.management.commands.test import Command as DjangoTestCommand
|
||||||
|
from django_yunohost_integration.local_test import CreateResults, create_local_test
|
||||||
from manageprojects.utilities import code_style
|
from manageprojects.utilities import code_style
|
||||||
from manageprojects.utilities.publish import publish_package
|
from manageprojects.utilities.publish import publish_package
|
||||||
from rich import print # noqa; noqa
|
from rich import print # noqa; noqa
|
||||||
|
@ -42,6 +45,7 @@ ARGUMENT_NOT_EXISTING_DIR = dict(
|
||||||
ARGUMENT_EXISTING_FILE = dict(
|
ARGUMENT_EXISTING_FILE = dict(
|
||||||
type=click.Path(exists=True, file_okay=True, dir_okay=False, readable=True, path_type=Path)
|
type=click.Path(exists=True, file_okay=True, dir_okay=False, readable=True, path_type=Path)
|
||||||
)
|
)
|
||||||
|
CLI_EPILOG = 'Project Homepage: https://github.com/YunoHost-Apps/pyinventory_ynh'
|
||||||
|
|
||||||
|
|
||||||
class ClickGroup(RichGroup): # FIXME: How to set the "info_name" easier?
|
class ClickGroup(RichGroup): # FIXME: How to set the "info_name" easier?
|
||||||
|
@ -50,10 +54,7 @@ class ClickGroup(RichGroup): # FIXME: How to set the "info_name" easier?
|
||||||
return super().make_context(info_name, *args, **kwargs)
|
return super().make_context(info_name, *args, **kwargs)
|
||||||
|
|
||||||
|
|
||||||
@click.group(
|
@click.group(cls=ClickGroup, epilog=CLI_EPILOG)
|
||||||
cls=ClickGroup,
|
|
||||||
epilog='Project Homepage: https://github.com/YunoHost-Apps/pyinventory_ynh',
|
|
||||||
)
|
|
||||||
def cli():
|
def cli():
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
@ -76,7 +77,7 @@ def coverage(verbose: bool = True):
|
||||||
"""
|
"""
|
||||||
verbose_check_call('coverage', 'run', verbose=verbose, exit_on_error=True)
|
verbose_check_call('coverage', 'run', verbose=verbose, exit_on_error=True)
|
||||||
verbose_check_call('coverage', 'combine', '--append', verbose=verbose, exit_on_error=True)
|
verbose_check_call('coverage', 'combine', '--append', verbose=verbose, exit_on_error=True)
|
||||||
verbose_check_call('coverage', 'report', '--fail-under=30', verbose=verbose, exit_on_error=True)
|
verbose_check_call('coverage', 'report', '--fail-under=10', verbose=verbose, exit_on_error=True)
|
||||||
verbose_check_call('coverage', 'xml', verbose=verbose, exit_on_error=True)
|
verbose_check_call('coverage', 'xml', verbose=verbose, exit_on_error=True)
|
||||||
verbose_check_call('coverage', 'json', verbose=verbose, exit_on_error=True)
|
verbose_check_call('coverage', 'json', verbose=verbose, exit_on_error=True)
|
||||||
|
|
||||||
|
@ -163,7 +164,10 @@ def publish():
|
||||||
"""
|
"""
|
||||||
Build and upload this project to PyPi
|
Build and upload this project to PyPi
|
||||||
"""
|
"""
|
||||||
_run_unittest_cli(verbose=False, exit_after_run=False) # Don't publish a broken state
|
try:
|
||||||
|
_run_django_test_cli() # Don't publish a broken state
|
||||||
|
except SystemExit as err:
|
||||||
|
assert err.code == 0, f'Exit code is not 0: {err.code}'
|
||||||
|
|
||||||
publish_package(
|
publish_package(
|
||||||
module=pyinventory_ynh,
|
module=pyinventory_ynh,
|
||||||
|
@ -217,14 +221,10 @@ def update_test_snapshot_files():
|
||||||
print(f'{removed_file_count} test snapshot files removed... run tests...')
|
print(f'{removed_file_count} test snapshot files removed... run tests...')
|
||||||
|
|
||||||
# Just recreate them by running tests:
|
# Just recreate them by running tests:
|
||||||
_run_unittest_cli(
|
os.environ['RAISE_SNAPSHOT_ERRORS'] = '0' # Recreate snapshot files without error
|
||||||
extra_env=dict(
|
try:
|
||||||
RAISE_SNAPSHOT_ERRORS='0', # Recreate snapshot files without error
|
_run_django_test_cli()
|
||||||
),
|
finally:
|
||||||
verbose=False,
|
|
||||||
exit_after_run=False,
|
|
||||||
)
|
|
||||||
|
|
||||||
new_files = len(list(iter_snapshot_files()))
|
new_files = len(list(iter_snapshot_files()))
|
||||||
print(f'{new_files} test snapshot files created, ok.\n')
|
print(f'{new_files} test snapshot files created, ok.\n')
|
||||||
|
|
||||||
|
@ -232,49 +232,48 @@ def update_test_snapshot_files():
|
||||||
cli.add_command(update_test_snapshot_files)
|
cli.add_command(update_test_snapshot_files)
|
||||||
|
|
||||||
|
|
||||||
def _run_unittest_cli(extra_env=None, verbose=True, exit_after_run=True):
|
def _run_django_test_cli():
|
||||||
"""
|
"""
|
||||||
Call the origin unittest CLI and pass all args to it.
|
Call the origin Django test manage command CLI and pass all args to it.
|
||||||
"""
|
"""
|
||||||
if extra_env is None:
|
os.environ['DJANGO_SETTINGS_MODULE'] = 'settings'
|
||||||
extra_env = dict()
|
|
||||||
|
|
||||||
extra_env.update(
|
print('Compile YunoHost files...')
|
||||||
dict(
|
result: CreateResults = create_local_test(
|
||||||
PYTHONUNBUFFERED='1',
|
django_settings_path=PACKAGE_ROOT / 'conf' / 'settings.py',
|
||||||
PYTHONWARNINGS='always',
|
destination=PACKAGE_ROOT / 'local_test',
|
||||||
)
|
runserver=False,
|
||||||
|
extra_replacements={
|
||||||
|
'__DEBUG_ENABLED__': '0', # "1" or "0" string
|
||||||
|
'__LOG_LEVEL__': 'INFO',
|
||||||
|
'__ADMIN_EMAIL__': 'foo-bar@test.tld',
|
||||||
|
'__DEFAULT_FROM_EMAIL__': 'django_app@test.tld',
|
||||||
|
},
|
||||||
)
|
)
|
||||||
|
print('Local test files created:')
|
||||||
|
print(result)
|
||||||
|
|
||||||
args = sys.argv[2:]
|
data_dir = str(result.data_dir_path)
|
||||||
if not args:
|
if data_dir not in sys.path:
|
||||||
if verbose:
|
sys.path.insert(0, data_dir)
|
||||||
args = ('--verbose', '--locals', '--buffer')
|
|
||||||
else:
|
|
||||||
args = ('--locals', '--buffer')
|
|
||||||
|
|
||||||
verbose_check_call(
|
django.setup()
|
||||||
sys.executable,
|
|
||||||
'-m',
|
os.chdir(Path(pyinventory_ynh.__file__).parent)
|
||||||
'unittest',
|
|
||||||
*args,
|
test_command = DjangoTestCommand()
|
||||||
timeout=15 * 60,
|
test_command.run_from_argv(sys.argv)
|
||||||
extra_env=extra_env,
|
|
||||||
)
|
|
||||||
if exit_after_run:
|
|
||||||
sys.exit(0)
|
|
||||||
|
|
||||||
|
|
||||||
@click.command() # Dummy command
|
@click.command() # Dummy command
|
||||||
def test():
|
def test():
|
||||||
"""
|
"""
|
||||||
Run unittests
|
Compile YunoHost files and run Django unittests
|
||||||
"""
|
"""
|
||||||
_run_unittest_cli()
|
_run_django_test_cli()
|
||||||
|
|
||||||
|
|
||||||
# TODO: Replace pytest with normal Django unittests:
|
cli.add_command(test)
|
||||||
# cli.add_command(test)
|
|
||||||
|
|
||||||
|
|
||||||
def _run_tox():
|
def _run_tox():
|
||||||
|
@ -290,7 +289,7 @@ def tox():
|
||||||
_run_tox()
|
_run_tox()
|
||||||
|
|
||||||
|
|
||||||
# TODO: cli.add_command(tox)
|
cli.add_command(tox)
|
||||||
|
|
||||||
|
|
||||||
@click.command()
|
@click.command()
|
||||||
|
@ -336,35 +335,30 @@ def diffsettings():
|
||||||
},
|
},
|
||||||
)
|
)
|
||||||
app_path = destination / 'opt_yunohost'
|
app_path = destination / 'opt_yunohost'
|
||||||
verbose_check_call(sys.executable, app_path / 'manage.py', 'diffsettings', cwd=app_path)
|
verbose_check_call(
|
||||||
|
sys.executable,
|
||||||
|
app_path / 'manage.py',
|
||||||
|
'diffsettings',
|
||||||
|
cwd=app_path,
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
cli.add_command(diffsettings)
|
cli.add_command(diffsettings)
|
||||||
|
|
||||||
|
|
||||||
@click.command()
|
|
||||||
def pytest():
|
|
||||||
"""
|
|
||||||
Run tests via "pytest"
|
|
||||||
"""
|
|
||||||
verbose_check_call(sys.executable, '-m', 'pytest', *sys.argv[2:], cwd=PACKAGE_ROOT)
|
|
||||||
|
|
||||||
|
|
||||||
cli.add_command(pytest)
|
|
||||||
|
|
||||||
|
|
||||||
def main():
|
def main():
|
||||||
print_version(pyinventory_ynh)
|
print_version(pyinventory_ynh)
|
||||||
|
|
||||||
|
print(f'{sys.argv=}')
|
||||||
if len(sys.argv) >= 2:
|
if len(sys.argv) >= 2:
|
||||||
# Check if we just pass a command call
|
# Check if we just pass a command call
|
||||||
command = sys.argv[1]
|
command = sys.argv[1]
|
||||||
if command == 'test':
|
if command == 'test':
|
||||||
# TODO: Call: _run_unittest_cli()
|
_run_django_test_cli()
|
||||||
verbose_check_call(sys.executable, '-m', 'pytest', cwd=PACKAGE_ROOT)
|
|
||||||
sys.exit(0)
|
sys.exit(0)
|
||||||
elif command == 'tox':
|
elif command == 'tox':
|
||||||
_run_tox()
|
_run_tox()
|
||||||
|
sys.exit(0)
|
||||||
|
|
||||||
# Execute Click CLI:
|
print('Execute Click CLI')
|
||||||
cli()
|
cli()
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
from unittest.mock import patch
|
from unittest.mock import patch
|
||||||
|
|
||||||
from axes.models import AccessLog
|
from axes.models import AccessLog
|
||||||
from bx_django_utils.test_utils.html_assertion import HtmlAssertionMixin, assert_html_response_snapshot
|
from bx_django_utils.test_utils.html_assertion import assert_html_response_snapshot, HtmlAssertionMixin
|
||||||
from django.conf import LazySettings, settings
|
from django.conf import LazySettings, settings
|
||||||
from django.contrib.auth.models import User
|
from django.contrib.auth.models import User
|
||||||
from django.template.defaulttags import CsrfTokenNode
|
from django.template.defaulttags import CsrfTokenNode
|
||||||
|
@ -9,9 +9,7 @@ from django.test import override_settings
|
||||||
from django.test.testcases import TestCase
|
from django.test.testcases import TestCase
|
||||||
from django.urls.base import reverse
|
from django.urls.base import reverse
|
||||||
from django_yunohost_integration.test_utils import generate_basic_auth
|
from django_yunohost_integration.test_utils import generate_basic_auth
|
||||||
|
from inventory import __version__ as upstream_version
|
||||||
import inventory
|
|
||||||
|
|
||||||
|
|
||||||
@override_settings(DEBUG=False)
|
@override_settings(DEBUG=False)
|
||||||
class DjangoYnhTestCase(HtmlAssertionMixin, TestCase):
|
class DjangoYnhTestCase(HtmlAssertionMixin, TestCase):
|
||||||
|
@ -29,33 +27,22 @@ class DjangoYnhTestCase(HtmlAssertionMixin, TestCase):
|
||||||
|
|
||||||
assert str(settings.DATA_DIR_PATH).endswith('/local_test/opt_yunohost')
|
assert str(settings.DATA_DIR_PATH).endswith('/local_test/opt_yunohost')
|
||||||
assert str(settings.INSTALL_DIR_PATH).endswith('/local_test/var_www')
|
assert str(settings.INSTALL_DIR_PATH).endswith('/local_test/var_www')
|
||||||
assert str(settings.LOG_FILE_PATH).endswith('/local_test/var_log_pyinventory.log')
|
assert str(settings.LOG_FILE_PATH).endswith(
|
||||||
|
'/local_test/var_log_pyinventory.log'
|
||||||
|
), f'{settings.LOG_FILE_PATH=}'
|
||||||
|
|
||||||
assert settings.ROOT_URLCONF == 'urls'
|
assert settings.ROOT_URLCONF == 'urls'
|
||||||
assert reverse('admin:index') == '/app_path/'
|
|
||||||
|
|
||||||
def test_config_panel_settings(self):
|
def test_config_panel_settings(self):
|
||||||
# config_panel.toml settings, set via tests.conftest.pytest_configure():
|
# config_panel.toml settings, set via tests.conftest.pytest_configure():
|
||||||
assert settings.DEBUG_ENABLED == 'NO' and settings.DEBUG is False
|
assert settings.DEBUG_ENABLED == '0' and settings.DEBUG is False
|
||||||
assert settings.LOG_LEVEL == 'INFO'
|
assert settings.LOG_LEVEL == 'INFO'
|
||||||
assert settings.ADMIN_EMAIL == 'foo-bar@test.tld'
|
assert settings.ADMIN_EMAIL == 'foo-bar@test.tld'
|
||||||
assert settings.DEFAULT_FROM_EMAIL == 'django_app@test.tld'
|
assert settings.DEFAULT_FROM_EMAIL == 'django_app@test.tld'
|
||||||
|
|
||||||
def test_urls(self):
|
|
||||||
assert reverse('admin:index') == '/app_path/'
|
|
||||||
|
|
||||||
# Serve user uploads via django_tools.serve_media_app:
|
|
||||||
assert settings.MEDIA_URL == '/app_path/media/'
|
|
||||||
|
|
||||||
url = reverse(
|
|
||||||
'serve_media_app:serve-media',
|
|
||||||
kwargs={'user_token': 'token', 'path': 'foo/bar/'},
|
|
||||||
)
|
|
||||||
assert url == '/app_path/media/token/foo/bar/'
|
|
||||||
|
|
||||||
def test_auth(self):
|
def test_auth(self):
|
||||||
assert settings.PATH_URL == 'app_path'
|
self.assertEqual(settings.PATH_URL, 'app_path')
|
||||||
assert reverse('admin:index') == '/app_path/'
|
self.assertEqual(reverse('admin:index'), '/app_path/')
|
||||||
|
|
||||||
# SecurityMiddleware should redirects all non-HTTPS requests to HTTPS:
|
# SecurityMiddleware should redirects all non-HTTPS requests to HTTPS:
|
||||||
assert settings.SECURE_SSL_REDIRECT is True
|
assert settings.SECURE_SSL_REDIRECT is True
|
||||||
|
@ -68,7 +55,11 @@ class DjangoYnhTestCase(HtmlAssertionMixin, TestCase):
|
||||||
)
|
)
|
||||||
|
|
||||||
response = self.client.get('/app_path/', secure=True)
|
response = self.client.get('/app_path/', secure=True)
|
||||||
self.assertRedirects(response, expected_url='/app_path/login/?next=/app_path/', fetch_redirect_response=False)
|
self.assertRedirects(
|
||||||
|
response,
|
||||||
|
expected_url='/app_path/login/?next=%2Fapp_path%2F',
|
||||||
|
fetch_redirect_response=False,
|
||||||
|
)
|
||||||
|
|
||||||
def test_create_unknown_user(self):
|
def test_create_unknown_user(self):
|
||||||
assert User.objects.count() == 0
|
assert User.objects.count() == 0
|
||||||
|
@ -94,11 +85,16 @@ class DjangoYnhTestCase(HtmlAssertionMixin, TestCase):
|
||||||
self.assert_html_parts(
|
self.assert_html_parts(
|
||||||
response,
|
response,
|
||||||
parts=(
|
parts=(
|
||||||
f'<title>Site administration | PyInventory v{inventory.__version__}</title>',
|
f'<h1 id="site-name"><a href="/app_path/">PyInventory v{upstream_version}</a></h1>',
|
||||||
'<strong>test</strong>',
|
'<strong>test</strong>',
|
||||||
|
#
|
||||||
|
# Can create PyInventory model entries:
|
||||||
|
'<a class="addlink" href="/app_path/inventory/itemmodel/add/">Add</a>',
|
||||||
|
'<a class="addlink" href="/app_path/inventory/locationmodel/add/">Add</a>',
|
||||||
|
'<a class="addlink" href="/app_path/inventory/memomodel/add/">Add</a>',
|
||||||
),
|
),
|
||||||
)
|
)
|
||||||
assert_html_response_snapshot(response, query_selector='#container', validate=False)
|
assert_html_response_snapshot(response, query_selector='#main', validate=False)
|
||||||
|
|
||||||
def test_wrong_auth_user(self):
|
def test_wrong_auth_user(self):
|
||||||
assert User.objects.count() == 0
|
assert User.objects.count() == 0
|
||||||
|
@ -107,7 +103,7 @@ class DjangoYnhTestCase(HtmlAssertionMixin, TestCase):
|
||||||
self.client.cookies['SSOwAuthUser'] = 'test'
|
self.client.cookies['SSOwAuthUser'] = 'test'
|
||||||
|
|
||||||
response = self.client.get(
|
response = self.client.get(
|
||||||
path='/app_path/',
|
path='/app_path/admin/',
|
||||||
HTTP_REMOTE_USER='test',
|
HTTP_REMOTE_USER='test',
|
||||||
HTTP_AUTH_USER='foobar', # <<< wrong user name
|
HTTP_AUTH_USER='foobar', # <<< wrong user name
|
||||||
HTTP_AUTHORIZATION='basic dGVzdDp0ZXN0MTIz',
|
HTTP_AUTHORIZATION='basic dGVzdDp0ZXN0MTIz',
|
|
@ -0,0 +1,92 @@
|
||||||
|
<div class="main" id="main">
|
||||||
|
<div class="content" id="content-start" tabindex="-1">
|
||||||
|
<!-- Content -->
|
||||||
|
<div class="colMS" id="content">
|
||||||
|
<h1>
|
||||||
|
Site administration
|
||||||
|
</h1>
|
||||||
|
<div id="content-main">
|
||||||
|
<div class="app-inventory module">
|
||||||
|
<table>
|
||||||
|
<caption>
|
||||||
|
<a class="section" href="/app_path/inventory/" title="Models in the Inventory application">
|
||||||
|
Inventory
|
||||||
|
</a>
|
||||||
|
</caption>
|
||||||
|
<tr class="model-itemmodel">
|
||||||
|
<th scope="row">
|
||||||
|
<a href="/app_path/inventory/itemmodel/">
|
||||||
|
Items
|
||||||
|
</a>
|
||||||
|
</th>
|
||||||
|
<td>
|
||||||
|
<a class="addlink" href="/app_path/inventory/itemmodel/add/">
|
||||||
|
Add
|
||||||
|
</a>
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
<a class="changelink" href="/app_path/inventory/itemmodel/">
|
||||||
|
Change
|
||||||
|
</a>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
<tr class="model-locationmodel">
|
||||||
|
<th scope="row">
|
||||||
|
<a href="/app_path/inventory/locationmodel/">
|
||||||
|
Locations
|
||||||
|
</a>
|
||||||
|
</th>
|
||||||
|
<td>
|
||||||
|
<a class="addlink" href="/app_path/inventory/locationmodel/add/">
|
||||||
|
Add
|
||||||
|
</a>
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
<a class="changelink" href="/app_path/inventory/locationmodel/">
|
||||||
|
Change
|
||||||
|
</a>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
<tr class="model-memomodel">
|
||||||
|
<th scope="row">
|
||||||
|
<a href="/app_path/inventory/memomodel/">
|
||||||
|
Memos
|
||||||
|
</a>
|
||||||
|
</th>
|
||||||
|
<td>
|
||||||
|
<a class="addlink" href="/app_path/inventory/memomodel/add/">
|
||||||
|
Add
|
||||||
|
</a>
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
<a class="changelink" href="/app_path/inventory/memomodel/">
|
||||||
|
Change
|
||||||
|
</a>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div id="content-related">
|
||||||
|
<div class="module" id="recent-actions-module">
|
||||||
|
<h2>
|
||||||
|
Recent actions
|
||||||
|
</h2>
|
||||||
|
<h3>
|
||||||
|
My actions
|
||||||
|
</h3>
|
||||||
|
<p>
|
||||||
|
None available
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<br class="clear"/>
|
||||||
|
</div>
|
||||||
|
<!-- END Content -->
|
||||||
|
<div id="footer">
|
||||||
|
<a href="https://github.com/jedie/PyInventory">
|
||||||
|
https://github.com/jedie/PyInventory
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
|
@ -1,68 +1,104 @@
|
||||||
import subprocess
|
import os
|
||||||
from unittest import TestCase
|
|
||||||
|
|
||||||
from bx_py_utils.path import assert_is_file
|
|
||||||
from manageprojects.test_utils.click_cli_utils import subprocess_cli
|
|
||||||
from manageprojects.test_utils.project_setup import check_editor_config, get_py_max_line_length
|
|
||||||
from manageprojects.utilities import code_style
|
|
||||||
from packaging.version import Version
|
|
||||||
|
|
||||||
from pyinventory_ynh import __version__
|
|
||||||
from pyinventory_ynh.cli.dev import PACKAGE_ROOT
|
from pyinventory_ynh.cli.dev import PACKAGE_ROOT
|
||||||
|
|
||||||
|
|
||||||
|
try:
|
||||||
|
import tomllib # New in Python 3.11
|
||||||
|
except ImportError:
|
||||||
|
import tomli as tomllib
|
||||||
|
|
||||||
|
from bx_django_utils.filename import clean_filename
|
||||||
|
from bx_py_utils.path import assert_is_dir, assert_is_file
|
||||||
|
from django.test.testcases import TestCase
|
||||||
|
from django_tools.unittest_utils.project_setup import check_editor_config
|
||||||
|
from django_yunohost_integration.test_utils import assert_project_version
|
||||||
|
from inventory import __version__ as upstream_version
|
||||||
|
|
||||||
|
from pyinventory_ynh import __version__ as ynh_pkg_version
|
||||||
|
|
||||||
|
|
||||||
|
def assert_file_contains_string(file_path, string):
|
||||||
|
with file_path.open('r') as f:
|
||||||
|
for line in f:
|
||||||
|
if string in line:
|
||||||
|
return
|
||||||
|
raise AssertionError(f'File {file_path} does not contain {string!r} !')
|
||||||
|
|
||||||
|
|
||||||
class ProjectSetupTestCase(TestCase):
|
class ProjectSetupTestCase(TestCase):
|
||||||
|
@classmethod
|
||||||
|
def setUpClass(cls):
|
||||||
|
super().setUpClass()
|
||||||
|
|
||||||
|
manifest_path = PACKAGE_ROOT / 'manifest.toml'
|
||||||
|
assert_is_file(manifest_path)
|
||||||
|
|
||||||
|
cls.manifest_cfg = tomllib.loads(manifest_path.read_text(encoding='UTF-8'))
|
||||||
|
|
||||||
def test_version(self):
|
def test_version(self):
|
||||||
self.assertIsNotNone(__version__)
|
assert ynh_pkg_version.startswith(
|
||||||
|
upstream_version
|
||||||
|
), f'{ynh_pkg_version=} does not start with {upstream_version=}'
|
||||||
|
self.assertIn('+ynh', ynh_pkg_version)
|
||||||
|
|
||||||
version = Version(__version__) # Will raise InvalidVersion() if wrong formatted
|
# pyproject.toml needs a PEP 440 conform version and used "+ynh"
|
||||||
self.assertEqual(str(version), __version__)
|
# the YunoHost syntax is: "~ynh", just "convert this:
|
||||||
|
manifest_version = ynh_pkg_version.replace('+', '~')
|
||||||
|
self.assertEqual(self.manifest_cfg['version'], manifest_version)
|
||||||
|
|
||||||
dev_cli_bin = PACKAGE_ROOT / 'dev-cli.py'
|
if 'GITHUB_ACTION' not in os.environ:
|
||||||
assert_is_file(dev_cli_bin)
|
# Github has a rate-limiting... So don't fetch the API if we run as GitHub action
|
||||||
|
assert_project_version(
|
||||||
output = subprocess.check_output([dev_cli_bin, 'version'], text=True)
|
current_version=ynh_pkg_version,
|
||||||
self.assertIn(f'pyinventory_ynh v{__version__}', output)
|
github_project_url='https://github.com/jedie/PyInventory',
|
||||||
|
|
||||||
def test_code_style(self):
|
|
||||||
dev_cli_bin = PACKAGE_ROOT / 'dev-cli.py'
|
|
||||||
assert_is_file(dev_cli_bin)
|
|
||||||
|
|
||||||
try:
|
|
||||||
output = subprocess_cli(
|
|
||||||
cli_bin=dev_cli_bin,
|
|
||||||
args=('check-code-style',),
|
|
||||||
exit_on_error=False,
|
|
||||||
)
|
)
|
||||||
except subprocess.CalledProcessError as err:
|
|
||||||
self.assertIn('.venv/bin/darker', err.stdout) # darker was called?
|
|
||||||
else:
|
|
||||||
if 'Code style: OK' in output:
|
|
||||||
self.assertIn('.venv/bin/darker', output) # darker was called?
|
|
||||||
return # Nothing to fix -> OK
|
|
||||||
|
|
||||||
# Try to "auto" fix code style:
|
def test_screenshot_filenames(self):
|
||||||
|
"""
|
||||||
try:
|
https://forum.yunohost.org/t/yunohost-bot-cant-handle-spaces-in-screenshots/19483
|
||||||
output = subprocess_cli(
|
"""
|
||||||
cli_bin=dev_cli_bin,
|
screenshot_path = PACKAGE_ROOT / 'doc' / 'screenshots'
|
||||||
args=('fix-code-style',),
|
assert_is_dir(screenshot_path)
|
||||||
exit_on_error=False,
|
renamed = []
|
||||||
)
|
for file_path in screenshot_path.iterdir():
|
||||||
except subprocess.CalledProcessError as err:
|
file_name = file_path.name
|
||||||
output = err.stdout
|
if file_name.startswith('.'):
|
||||||
|
continue
|
||||||
self.assertIn('.venv/bin/darker', output) # darker was called?
|
cleaned_name = clean_filename(file_name)
|
||||||
|
if cleaned_name != file_name:
|
||||||
# Check again and display the output:
|
new_path = file_path.with_name(cleaned_name)
|
||||||
|
file_path.rename(new_path)
|
||||||
try:
|
renamed.append(f'{file_name!r} renamed to {cleaned_name!r}')
|
||||||
code_style.check(package_root=PACKAGE_ROOT)
|
assert not renamed, f'Bad screenshots file names found: {", ".join(renamed)}'
|
||||||
except SystemExit as err:
|
|
||||||
self.assertEqual(err.code, 0, 'Code style error, see output above!')
|
|
||||||
|
|
||||||
def test_check_editor_config(self):
|
def test_check_editor_config(self):
|
||||||
check_editor_config(package_root=PACKAGE_ROOT)
|
check_editor_config(package_root=PACKAGE_ROOT)
|
||||||
|
|
||||||
max_line_length = get_py_max_line_length(package_root=PACKAGE_ROOT)
|
def test_manifest_toml(self):
|
||||||
self.assertEqual(max_line_length, 119)
|
self.assertEqual(self.manifest_cfg['packaging_format'], 2)
|
||||||
|
self.assertEqual(
|
||||||
|
set(self.manifest_cfg['install'].keys()),
|
||||||
|
{
|
||||||
|
'admin',
|
||||||
|
'admin_email',
|
||||||
|
'debug_enabled',
|
||||||
|
'default_from_email',
|
||||||
|
'domain',
|
||||||
|
'init_main_permission',
|
||||||
|
'log_level',
|
||||||
|
'path',
|
||||||
|
},
|
||||||
|
)
|
||||||
|
self.assertEqual(
|
||||||
|
set(self.manifest_cfg['resources'].keys()),
|
||||||
|
{
|
||||||
|
'apt',
|
||||||
|
'data_dir',
|
||||||
|
'database',
|
||||||
|
'install_dir',
|
||||||
|
'permissions',
|
||||||
|
'ports',
|
||||||
|
'system_user',
|
||||||
|
},
|
||||||
|
)
|
||||||
|
|
36
pyinventory_ynh/tests/test_readme.py
Normal file
36
pyinventory_ynh/tests/test_readme.py
Normal file
|
@ -0,0 +1,36 @@
|
||||||
|
from pathlib import Path
|
||||||
|
|
||||||
|
from bx_py_utils.auto_doc import assert_readme_block
|
||||||
|
from manageprojects.test_utils.click_cli_utils import invoke_click
|
||||||
|
from manageprojects.tests.base import BaseTestCase
|
||||||
|
|
||||||
|
from pyinventory_ynh.cli.dev import CLI_EPILOG, PACKAGE_ROOT, cli
|
||||||
|
|
||||||
|
|
||||||
|
def assert_cli_help_in_readme(text_block: str, marker: str, readme_path: Path):
|
||||||
|
text_block = text_block.replace(CLI_EPILOG, '')
|
||||||
|
text_block = f'```\n{text_block.strip()}\n```'
|
||||||
|
assert_readme_block(
|
||||||
|
readme_path=readme_path,
|
||||||
|
text_block=text_block,
|
||||||
|
start_marker_line=f'[comment]: <> (✂✂✂ auto generated {marker} start ✂✂✂)',
|
||||||
|
end_marker_line=f'[comment]: <> (✂✂✂ auto generated {marker} end ✂✂✂)',
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
class ReadmeTestCase(BaseTestCase):
|
||||||
|
def test_main_help(self):
|
||||||
|
stdout = invoke_click(cli, '--help')
|
||||||
|
self.assert_in_content(
|
||||||
|
got=stdout,
|
||||||
|
parts=(
|
||||||
|
'Usage: ./dev-cli.py [OPTIONS] COMMAND [ARGS]...',
|
||||||
|
' local-test ',
|
||||||
|
CLI_EPILOG,
|
||||||
|
),
|
||||||
|
)
|
||||||
|
assert_cli_help_in_readme(
|
||||||
|
text_block=stdout,
|
||||||
|
marker='help',
|
||||||
|
readme_path=PACKAGE_ROOT / 'doc' / 'ADMIN.md',
|
||||||
|
)
|
|
@ -25,14 +25,9 @@ dependencies = [
|
||||||
dev = [
|
dev = [
|
||||||
"bx_django_utils", # https://github.com/boxine/bx_django_utils
|
"bx_django_utils", # https://github.com/boxine/bx_django_utils
|
||||||
"beautifulsoup4", # https://pypi.org/project/beautifulsoup4/
|
"beautifulsoup4", # https://pypi.org/project/beautifulsoup4/
|
||||||
#
|
|
||||||
# TODO: Remove "pytest" and use normal unittests ;)
|
|
||||||
"pytest",
|
|
||||||
"pytest-cov",
|
|
||||||
"pytest-django",
|
|
||||||
#
|
|
||||||
"manageprojects>=0.15.0", # https://github.com/jedie/manageprojects
|
"manageprojects>=0.15.0", # https://github.com/jedie/manageprojects
|
||||||
"pip-tools", # https://github.com/jazzband/pip-tools/
|
"pip-tools", # https://github.com/jazzband/pip-tools/
|
||||||
|
"tblib", # https://github.com/ionelmc/python-tblib
|
||||||
"tox", # https://github.com/tox-dev/tox
|
"tox", # https://github.com/tox-dev/tox
|
||||||
"coverage", # https://github.com/nedbat/coveragepy
|
"coverage", # https://github.com/nedbat/coveragepy
|
||||||
"autopep8", # https://github.com/hhatto/autopep8
|
"autopep8", # https://github.com/hhatto/autopep8
|
||||||
|
@ -56,7 +51,6 @@ dev = [
|
||||||
# to avoid errors like:
|
# to avoid errors like:
|
||||||
# In --require-hashes mode, all requirements must have their versions pinned with ==. These do not: ...
|
# In --require-hashes mode, all requirements must have their versions pinned with ==. These do not: ...
|
||||||
"tomli", # Only needed for Python <3.11
|
"tomli", # Only needed for Python <3.11
|
||||||
"exceptiongroup", # needed by pytest
|
|
||||||
]
|
]
|
||||||
|
|
||||||
[project.urls]
|
[project.urls]
|
||||||
|
@ -103,52 +97,23 @@ log_level = "INFO"
|
||||||
atomic=true
|
atomic=true
|
||||||
profile='black'
|
profile='black'
|
||||||
skip_glob=[".*", "*/htmlcov/*","*/migrations/*","*/local_test/*"]
|
skip_glob=[".*", "*/htmlcov/*","*/migrations/*","*/local_test/*"]
|
||||||
known_first_party=['inventory', 'inventory_project', 'pyinventory_ynh']
|
known_first_party=['pyinventory', 'pyinventory_ynh']
|
||||||
line_length=119
|
line_length=119
|
||||||
lines_after_imports=2
|
lines_after_imports=2
|
||||||
|
|
||||||
|
|
||||||
[tool.pytest.ini_options]
|
|
||||||
# https://docs.pytest.org/en/latest/customize.html#pyproject-toml
|
|
||||||
minversion = "6.0"
|
|
||||||
norecursedirs = ".* .git __pycache__ conf local_test coverage* dist htmlcov"
|
|
||||||
# sometimes helpfull "addopts" arguments:
|
|
||||||
# -vv
|
|
||||||
# --verbose
|
|
||||||
# --capture=no
|
|
||||||
# --trace-config
|
|
||||||
# --full-trace
|
|
||||||
# -p no:warnings
|
|
||||||
addopts = """
|
|
||||||
--reuse-db
|
|
||||||
--nomigrations
|
|
||||||
--cov=.
|
|
||||||
--cov-config=pyproject.toml
|
|
||||||
--cov-report term-missing
|
|
||||||
--cov-report html
|
|
||||||
--cov-report xml
|
|
||||||
--no-cov-on-fail
|
|
||||||
--showlocals
|
|
||||||
--doctest-modules
|
|
||||||
--failed-first
|
|
||||||
--new-first
|
|
||||||
"""
|
|
||||||
|
|
||||||
|
|
||||||
[tool.coverage.run]
|
[tool.coverage.run]
|
||||||
branch = true
|
branch = true
|
||||||
parallel = true
|
parallel = true
|
||||||
concurrency = ["multiprocessing"]
|
concurrency = ["multiprocessing"]
|
||||||
source = ['.']
|
source = ['.']
|
||||||
# TODO: pytest -> Django unitests:
|
command_line = './dev-cli.py test'
|
||||||
#command_line = '-m unittest --verbose --locals --buffer'
|
|
||||||
command_line = '-m pytest'
|
|
||||||
disable_warnings = ["couldnt-parse"]
|
disable_warnings = ["couldnt-parse"]
|
||||||
|
|
||||||
[tool.coverage.report]
|
[tool.coverage.report]
|
||||||
omit = ['.*', '*/tests/*']
|
omit = ['.*', '*/tests/*']
|
||||||
skip_empty = true
|
skip_empty = true
|
||||||
fail_under = 30
|
fail_under = 10
|
||||||
show_missing = true
|
show_missing = true
|
||||||
exclude_lines = [
|
exclude_lines = [
|
||||||
'if self.debug:',
|
'if self.debug:',
|
||||||
|
@ -213,4 +178,8 @@ applied_migrations = [
|
||||||
"877e2ec", # 2023-08-17T20:54:24+02:00
|
"877e2ec", # 2023-08-17T20:54:24+02:00
|
||||||
"be3f649", # 2023-08-22T19:36:57+02:00
|
"be3f649", # 2023-08-22T19:36:57+02:00
|
||||||
"c1a9d97", # 2023-11-01T19:59:17+01:00
|
"c1a9d97", # 2023-11-01T19:59:17+01:00
|
||||||
|
"0a5d693", # 2023-11-25T15:06:21+01:00
|
||||||
|
"6b89813", # 2023-11-25T15:23:07+01:00
|
||||||
|
"4abd4c0", # 2023-11-25T15:59:31+01:00
|
||||||
|
"2f9fd7b", # 2023-11-26T20:13:32+01:00
|
||||||
]
|
]
|
||||||
|
|
|
@ -66,9 +66,9 @@ build==1.0.3 \
|
||||||
--hash=sha256:538aab1b64f9828977f84bc63ae570b060a8ed1be419e7870b8b4fc5e6ea553b \
|
--hash=sha256:538aab1b64f9828977f84bc63ae570b060a8ed1be419e7870b8b4fc5e6ea553b \
|
||||||
--hash=sha256:589bf99a67df7c9cf07ec0ac0e5e2ea5d4b37ac63301c4986d1acb126aa83f8f
|
--hash=sha256:589bf99a67df7c9cf07ec0ac0e5e2ea5d4b37ac63301c4986d1acb126aa83f8f
|
||||||
# via pip-tools
|
# via pip-tools
|
||||||
bx-django-utils==67 \
|
bx-django-utils==69 \
|
||||||
--hash=sha256:8740fdaf98ed68a8ddb3af025d9b4f87c99101405898ddca86810b0c384b215a \
|
--hash=sha256:39e96b8ad47bcf36d6713e4e42c8d09deb21e413160dc2944f17b7d2e2244713 \
|
||||||
--hash=sha256:aca0ae5c91a62e4f594172b8c43468c701516f99ae50d99412d5299ba375df03
|
--hash=sha256:59b806aa36b50184f14bd0f7a61fb66c478fa231a44f92472360ce0cf1616013
|
||||||
# via
|
# via
|
||||||
# pyinventory
|
# pyinventory
|
||||||
# pyinventory-ynh (pyproject.toml)
|
# pyinventory-ynh (pyproject.toml)
|
||||||
|
@ -84,9 +84,9 @@ cachetools==5.3.2 \
|
||||||
--hash=sha256:086ee420196f7b2ab9ca2db2520aca326318b68fe5ba8bc4d49cca91add450f2 \
|
--hash=sha256:086ee420196f7b2ab9ca2db2520aca326318b68fe5ba8bc4d49cca91add450f2 \
|
||||||
--hash=sha256:861f35a13a451f94e301ce2bec7cac63e881232ccce7ed67fab9b5df4d3beaa1
|
--hash=sha256:861f35a13a451f94e301ce2bec7cac63e881232ccce7ed67fab9b5df4d3beaa1
|
||||||
# via tox
|
# via tox
|
||||||
certifi==2023.7.22 \
|
certifi==2023.11.17 \
|
||||||
--hash=sha256:539cc1d13202e33ca466e88b2807e29f4c13049d6d87031a3c110744495cb082 \
|
--hash=sha256:9b469f3a900bf28dc19b8cfbf8019bf47f7fdd1a65a1d4ffb98fc14166beb4d1 \
|
||||||
--hash=sha256:92d6037539857d8206b8f6ae472e8b77db8058fec5937a1ef3f54304089edbb9
|
--hash=sha256:e036ab49d5b79556f99cfc2d9320b34cfbe5be05c5871b51de9329f0603b0474
|
||||||
# via requests
|
# via requests
|
||||||
cffi==1.16.0 \
|
cffi==1.16.0 \
|
||||||
--hash=sha256:0c9ef6ff37e974b73c25eecc13952c55bceed9112be2d9d938ded8e856138bcc \
|
--hash=sha256:0c9ef6ff37e974b73c25eecc13952c55bceed9112be2d9d938ded8e856138bcc \
|
||||||
|
@ -273,11 +273,11 @@ colorlog==6.7.0 \
|
||||||
# via
|
# via
|
||||||
# django-yunohost-integration
|
# django-yunohost-integration
|
||||||
# pyinventory
|
# pyinventory
|
||||||
cookiecutter==2.4.0 \
|
cookiecutter==2.5.0 \
|
||||||
--hash=sha256:6d1494e66a784f23324df9d593f3e43af3db4f4b926b9e49e6ff060169fc042a \
|
--hash=sha256:8aa2f12ed11bc05628651e9dc4353a10571dd9908aaaaeec959a2b9ea465a5d2 \
|
||||||
--hash=sha256:8344663028abc08ec09b912e663636a97e1775bffe973425ec0107431acd390e
|
--hash=sha256:e61e9034748e3f41b8bd2c11f00d030784b48711c4d5c42363c50989a65331ec
|
||||||
# via manageprojects
|
# via manageprojects
|
||||||
coverage[toml]==7.3.2 \
|
coverage==7.3.2 \
|
||||||
--hash=sha256:0cbf38419fb1a347aaf63481c00f0bdc86889d9fbf3f25109cf96c26b403fda1 \
|
--hash=sha256:0cbf38419fb1a347aaf63481c00f0bdc86889d9fbf3f25109cf96c26b403fda1 \
|
||||||
--hash=sha256:12d15ab5833a997716d76f2ac1e4b4d536814fc213c85ca72756c19e5a6b3d63 \
|
--hash=sha256:12d15ab5833a997716d76f2ac1e4b4d536814fc213c85ca72756c19e5a6b3d63 \
|
||||||
--hash=sha256:149de1d2401ae4655c436a3dced6dd153f4c3309f599c3d4bd97ab172eaf02d9 \
|
--hash=sha256:149de1d2401ae4655c436a3dced6dd153f4c3309f599c3d4bd97ab172eaf02d9 \
|
||||||
|
@ -330,9 +330,7 @@ coverage[toml]==7.3.2 \
|
||||||
--hash=sha256:f94b734214ea6a36fe16e96a70d941af80ff3bfd716c141300d95ebc85339738 \
|
--hash=sha256:f94b734214ea6a36fe16e96a70d941af80ff3bfd716c141300d95ebc85339738 \
|
||||||
--hash=sha256:fa28e909776dc69efb6ed975a63691bc8172b64ff357e663a1bb06ff3c9b589a \
|
--hash=sha256:fa28e909776dc69efb6ed975a63691bc8172b64ff357e663a1bb06ff3c9b589a \
|
||||||
--hash=sha256:fe494faa90ce6381770746077243231e0b83ff3f17069d748f645617cefe19d4
|
--hash=sha256:fe494faa90ce6381770746077243231e0b83ff3f17069d748f645617cefe19d4
|
||||||
# via
|
# via pyinventory-ynh (pyproject.toml)
|
||||||
# pyinventory-ynh (pyproject.toml)
|
|
||||||
# pytest-cov
|
|
||||||
cryptography==41.0.5 \
|
cryptography==41.0.5 \
|
||||||
--hash=sha256:0c327cac00f082013c7c9fb6c46b7cc9fa3c288ca702c74773968173bda421bf \
|
--hash=sha256:0c327cac00f082013c7c9fb6c46b7cc9fa3c288ca702c74773968173bda421bf \
|
||||||
--hash=sha256:0d2a6a598847c46e3e321a7aef8af1436f11c27f1254933746304ff014664d84 \
|
--hash=sha256:0d2a6a598847c46e3e321a7aef8af1436f11c27f1254933746304ff014664d84 \
|
||||||
|
@ -417,9 +415,9 @@ django-debug-toolbar==4.2.0 \
|
||||||
--hash=sha256:af99128c06e8e794479e65ab62cc6c7d1e74e1c19beb44dcbf9bad7a9c017327 \
|
--hash=sha256:af99128c06e8e794479e65ab62cc6c7d1e74e1c19beb44dcbf9bad7a9c017327 \
|
||||||
--hash=sha256:bc7fdaafafcdedefcc67a4a5ad9dac96efd6e41db15bc74d402a54a2ba4854dc
|
--hash=sha256:bc7fdaafafcdedefcc67a4a5ad9dac96efd6e41db15bc74d402a54a2ba4854dc
|
||||||
# via pyinventory
|
# via pyinventory
|
||||||
django-import-export==3.3.2 \
|
django-import-export==3.3.3 \
|
||||||
--hash=sha256:9a5c7c191014e4defb01573ee94864b60724a203f1b8a7e5e67a03f06b27b62d \
|
--hash=sha256:2c1b16e1cf2ea5f62a165d8867e7c6dcff25673ab7201fd18aaf67c9ee90367e \
|
||||||
--hash=sha256:d13e7508190f46442280bd7d04efcf49af6521350a70a6f9e06447ef28d6a41d
|
--hash=sha256:78973202e93897326ab0411d64eaf89b72779fcb21ee9e5f64f3fb96571a5978
|
||||||
# via pyinventory
|
# via pyinventory
|
||||||
django-js-asset==2.1.0 \
|
django-js-asset==2.1.0 \
|
||||||
--hash=sha256:36a3a4dd6e9efc895fb127d13126020f6ec1ec9469ad42878d42143f22495d90 \
|
--hash=sha256:36a3a4dd6e9efc895fb127d13126020f6ec1ec9469ad42878d42143f22495d90 \
|
||||||
|
@ -471,10 +469,6 @@ et-xmlfile==1.1.0 \
|
||||||
--hash=sha256:8eb9e2bc2f8c97e37a2dc85a09ecdcdec9d8a396530a6d5a33b30b9a92da0c5c \
|
--hash=sha256:8eb9e2bc2f8c97e37a2dc85a09ecdcdec9d8a396530a6d5a33b30b9a92da0c5c \
|
||||||
--hash=sha256:a2ba85d1d6a74ef63837eed693bcb89c3f752169b0e3e7ae5b16ca5e1b3deada
|
--hash=sha256:a2ba85d1d6a74ef63837eed693bcb89c3f752169b0e3e7ae5b16ca5e1b3deada
|
||||||
# via openpyxl
|
# via openpyxl
|
||||||
exceptiongroup==1.1.3 \
|
|
||||||
--hash=sha256:097acd85d473d75af5bb98e41b61ff7fe35efe6675e4f9370ec6ec5126d160e9 \
|
|
||||||
--hash=sha256:343280667a4585d195ca1cf9cef84a4e178c4b6cf2274caef9859782b567d5e3
|
|
||||||
# via pyinventory-ynh (pyproject.toml)
|
|
||||||
filelock==3.13.1 \
|
filelock==3.13.1 \
|
||||||
--hash=sha256:521f5f56c50f8426f5e03ad3b281b490a87ef15bc6c526f168290f0c7148d44e \
|
--hash=sha256:521f5f56c50f8426f5e03ad3b281b490a87ef15bc6c526f168290f0c7148d44e \
|
||||||
--hash=sha256:57dbda9b35157b05fb3e58ee91448612eb674172fab98ee235ccb0b5bee19a1c
|
--hash=sha256:57dbda9b35157b05fb3e58ee91448612eb674172fab98ee235ccb0b5bee19a1c
|
||||||
|
@ -501,9 +495,9 @@ icdiff==2.0.7 \
|
||||||
--hash=sha256:f05d1b3623223dd1c70f7848da7d699de3d9a2550b902a8234d9026292fb5762 \
|
--hash=sha256:f05d1b3623223dd1c70f7848da7d699de3d9a2550b902a8234d9026292fb5762 \
|
||||||
--hash=sha256:f79a318891adbf59a45e3a7694f5e1f18c5407065264637072ac8363b759866f
|
--hash=sha256:f79a318891adbf59a45e3a7694f5e1f18c5407065264637072ac8363b759866f
|
||||||
# via django-tools
|
# via django-tools
|
||||||
idna==3.4 \
|
idna==3.6 \
|
||||||
--hash=sha256:814f528e8dead7d329833b91c5faa87d60bf71824cd12a7530b5526063d02cb4 \
|
--hash=sha256:9ecdbbd083b06798ae1e86adcbfe8ab1479cf864e4ee30fe4e46a003d12491ca \
|
||||||
--hash=sha256:90b77e79eaa3eba6de819a0c442c0b4ceefc341a7a2ab77d7562bf49f425c5c2
|
--hash=sha256:c05567e9c24a6b9faaa835c4821bad0590fbb9d5779e7caa6e1cc4978e7eb24f
|
||||||
# via requests
|
# via requests
|
||||||
importlib-metadata==6.8.0 \
|
importlib-metadata==6.8.0 \
|
||||||
--hash=sha256:3ebb78df84a805d7698245025b975d9d67053cd94c79245ba4b3eb694abe68bb \
|
--hash=sha256:3ebb78df84a805d7698245025b975d9d67053cd94c79245ba4b3eb694abe68bb \
|
||||||
|
@ -511,10 +505,6 @@ importlib-metadata==6.8.0 \
|
||||||
# via
|
# via
|
||||||
# keyring
|
# keyring
|
||||||
# twine
|
# twine
|
||||||
iniconfig==2.0.0 \
|
|
||||||
--hash=sha256:2d91e135bf72d31a410b17c16da610a82cb55f6b0477d1a902134b24a455b8b3 \
|
|
||||||
--hash=sha256:b6a85871a79d2e3b22d2d1b94ac2824226a63c6b741c88f7ae975f18b6778374
|
|
||||||
# via pytest
|
|
||||||
isort==5.12.0 \
|
isort==5.12.0 \
|
||||||
--hash=sha256:8bef7dde241278824a6d83f44a544709b065191b95b6e50894bdc722fcba0504 \
|
--hash=sha256:8bef7dde241278824a6d83f44a544709b065191b95b6e50894bdc722fcba0504 \
|
||||||
--hash=sha256:f84c2818376e66cf843d497486ea8fed8700b340f308f076c6fb1229dff318b6
|
--hash=sha256:f84c2818376e66cf843d497486ea8fed8700b340f308f076c6fb1229dff318b6
|
||||||
|
@ -533,13 +523,13 @@ jinja2==3.1.2 \
|
||||||
--hash=sha256:31351a702a408a9e7595a8fc6150fc3f43bb6bf7e319770cbc0db9df9437e852 \
|
--hash=sha256:31351a702a408a9e7595a8fc6150fc3f43bb6bf7e319770cbc0db9df9437e852 \
|
||||||
--hash=sha256:6088930bfe239f0e6710546ab9c19c9ef35e29792895fed6e6e31a023a182a61
|
--hash=sha256:6088930bfe239f0e6710546ab9c19c9ef35e29792895fed6e6e31a023a182a61
|
||||||
# via cookiecutter
|
# via cookiecutter
|
||||||
keyring==24.2.0 \
|
keyring==24.3.0 \
|
||||||
--hash=sha256:4901caaf597bfd3bbd78c9a0c7c4c29fcd8310dab2cffefe749e916b6527acd6 \
|
--hash=sha256:4446d35d636e6a10b8bce7caa66913dd9eca5fd222ca03a3d42c38608ac30836 \
|
||||||
--hash=sha256:ca0746a19ec421219f4d713f848fa297a661a8a8c1504867e55bfb5e09091509
|
--hash=sha256:e730ecffd309658a08ee82535a3b5ec4b4c8669a9be11efb66249d8e0aeb9a25
|
||||||
# via twine
|
# via twine
|
||||||
manageprojects==0.15.2 \
|
manageprojects==0.15.3 \
|
||||||
--hash=sha256:44ac8973f9fede20693bd52c062d3b780268001f146100e6f3fc1bbaaa9ba720 \
|
--hash=sha256:052fe4e6ce8d2e36f9ec9adaffce918874512a96e3b92bc53a5cb3bfbf3ad3ad \
|
||||||
--hash=sha256:f264f238e5f2998019e2a654103c28519110c47d509ba9652b77883148fe3c85
|
--hash=sha256:4f94b261efc2013848043aaac7282f1496ef6207681a4a9881b67bdc5388140d
|
||||||
# via pyinventory-ynh (pyproject.toml)
|
# via pyinventory-ynh (pyproject.toml)
|
||||||
markdown-it-py==3.0.0 \
|
markdown-it-py==3.0.0 \
|
||||||
--hash=sha256:355216845c60bd96232cd8d8c40e8f9765cc86f46880e43a8fd22dc1a1a8cab1 \
|
--hash=sha256:355216845c60bd96232cd8d8c40e8f9765cc86f46880e43a8fd22dc1a1a8cab1 \
|
||||||
|
@ -622,34 +612,34 @@ more-itertools==10.1.0 \
|
||||||
--hash=sha256:626c369fa0eb37bac0291bce8259b332fd59ac792fa5497b59837309cd5b114a \
|
--hash=sha256:626c369fa0eb37bac0291bce8259b332fd59ac792fa5497b59837309cd5b114a \
|
||||||
--hash=sha256:64e0735fcfdc6f3464ea133afe8ea4483b1c5fe3a3d69852e6503b43a0b222e6
|
--hash=sha256:64e0735fcfdc6f3464ea133afe8ea4483b1c5fe3a3d69852e6503b43a0b222e6
|
||||||
# via jaraco-classes
|
# via jaraco-classes
|
||||||
mypy==1.6.1 \
|
mypy==1.7.1 \
|
||||||
--hash=sha256:19f905bcfd9e167159b3d63ecd8cb5e696151c3e59a1742e79bc3bcb540c42c7 \
|
--hash=sha256:12cce78e329838d70a204293e7b29af9faa3ab14899aec397798a4b41be7f340 \
|
||||||
--hash=sha256:21a1ad938fee7d2d96ca666c77b7c494c3c5bd88dff792220e1afbebb2925b5e \
|
--hash=sha256:1484b8fa2c10adf4474f016e09d7a159602f3239075c7bf9f1627f5acf40ad49 \
|
||||||
--hash=sha256:40b1844d2e8b232ed92e50a4bd11c48d2daa351f9deee6c194b83bf03e418b0c \
|
--hash=sha256:204e0d6de5fd2317394a4eff62065614c4892d5a4d1a7ee55b765d7a3d9e3f82 \
|
||||||
--hash=sha256:41697773aa0bf53ff917aa077e2cde7aa50254f28750f9b88884acea38a16169 \
|
--hash=sha256:2643d145af5292ee956aa0a83c2ce1038a3bdb26e033dadeb2f7066fb0c9abce \
|
||||||
--hash=sha256:49ae115da099dcc0922a7a895c1eec82c1518109ea5c162ed50e3b3594c71208 \
|
--hash=sha256:2c6e4464ed5f01dc44dc9821caf67b60a4e5c3b04278286a85c067010653a0eb \
|
||||||
--hash=sha256:4c46b51de523817a0045b150ed11b56f9fff55f12b9edd0f3ed35b15a2809de0 \
|
--hash=sha256:2f7f6985d05a4e3ce8255396df363046c28bea790e40617654e91ed580ca7c51 \
|
||||||
--hash=sha256:4cbe68ef919c28ea561165206a2dcb68591c50f3bcf777932323bc208d949cf1 \
|
--hash=sha256:31902408f4bf54108bbfb2e35369877c01c95adc6192958684473658c322c8a5 \
|
||||||
--hash=sha256:4d01c00d09a0be62a4ca3f933e315455bde83f37f892ba4b08ce92f3cf44bcc1 \
|
--hash=sha256:40716d1f821b89838589e5b3106ebbc23636ffdef5abc31f7cd0266db936067e \
|
||||||
--hash=sha256:59a0d7d24dfb26729e0a068639a6ce3500e31d6655df8557156c51c1cb874ce7 \
|
--hash=sha256:4b901927f16224d0d143b925ce9a4e6b3a758010673eeded9b748f250cf4e8f7 \
|
||||||
--hash=sha256:68351911e85145f582b5aa6cd9ad666c8958bcae897a1bfda8f4940472463c45 \
|
--hash=sha256:4fc3d14ee80cd22367caaaf6e014494415bf440980a3045bf5045b525680ac33 \
|
||||||
--hash=sha256:7274b0c57737bd3476d2229c6389b2ec9eefeb090bbaf77777e9d6b1b5a9d143 \
|
--hash=sha256:5cf3f0c5ac72139797953bd50bc6c95ac13075e62dbfcc923571180bebb662e9 \
|
||||||
--hash=sha256:81af8adaa5e3099469e7623436881eff6b3b06db5ef75e6f5b6d4871263547e5 \
|
--hash=sha256:6dbdec441c60699288adf051f51a5d512b0d818526d1dcfff5a41f8cd8b4aaf1 \
|
||||||
--hash=sha256:82e469518d3e9a321912955cc702d418773a2fd1e91c651280a1bda10622f02f \
|
--hash=sha256:72cf32ce7dd3562373f78bd751f73c96cfb441de147cc2448a92c1a308bd0ca6 \
|
||||||
--hash=sha256:8b27958f8c76bed8edaa63da0739d76e4e9ad4ed325c814f9b3851425582a3cd \
|
--hash=sha256:75aa828610b67462ffe3057d4d8a4112105ed211596b750b53cbfe182f44777a \
|
||||||
--hash=sha256:8c223fa57cb154c7eab5156856c231c3f5eace1e0bed9b32a24696b7ba3c3245 \
|
--hash=sha256:75c4d2a6effd015786c87774e04331b6da863fc3fc4e8adfc3b40aa55ab516fe \
|
||||||
--hash=sha256:8f57e6b6927a49550da3d122f0cb983d400f843a8a82e65b3b380d3d7259468f \
|
--hash=sha256:78e25b2fd6cbb55ddfb8058417df193f0129cad5f4ee75d1502248e588d9e0d7 \
|
||||||
--hash=sha256:925cd6a3b7b55dfba252b7c4561892311c5358c6b5a601847015a1ad4eb7d332 \
|
--hash=sha256:84860e06ba363d9c0eeabd45ac0fde4b903ad7aa4f93cd8b648385a888e23200 \
|
||||||
--hash=sha256:a43ef1c8ddfdb9575691720b6352761f3f53d85f1b57d7745701041053deff30 \
|
--hash=sha256:8c5091ebd294f7628eb25ea554852a52058ac81472c921150e3a61cdd68f75a7 \
|
||||||
--hash=sha256:a8032e00ce71c3ceb93eeba63963b864bf635a18f6c0c12da6c13c450eedb183 \
|
--hash=sha256:944bdc21ebd620eafefc090cdf83158393ec2b1391578359776c00de00e8907a \
|
||||||
--hash=sha256:b96ae2c1279d1065413965c607712006205a9ac541895004a1e0d4f281f2ff9f \
|
--hash=sha256:9c7ac372232c928fff0645d85f273a726970c014749b924ce5710d7d89763a28 \
|
||||||
--hash=sha256:bb8ccb4724f7d8601938571bf3f24da0da791fe2db7be3d9e79849cb64e0ae85 \
|
--hash=sha256:d9b338c19fa2412f76e17525c1b4f2c687a55b156320acb588df79f2e6fa9fea \
|
||||||
--hash=sha256:bbaf4662e498c8c2e352da5f5bca5ab29d378895fa2d980630656178bd607c46 \
|
--hash=sha256:ee5d62d28b854eb61889cde4e1dbc10fbaa5560cb39780c3995f6737f7e82120 \
|
||||||
--hash=sha256:cfd13d47b29ed3bbaafaff7d8b21e90d827631afda134836962011acb5904b71 \
|
--hash=sha256:f2c2521a8e4d6d769e3234350ba7b65ff5d527137cdcde13ff4d99114b0c8e7d \
|
||||||
--hash=sha256:d4473c22cc296425bbbce7e9429588e76e05bc7342da359d6520b6427bf76660 \
|
--hash=sha256:f6efc9bd72258f89a3816e3a98c09d36f079c223aa345c659622f056b760ab42 \
|
||||||
--hash=sha256:d8fbb68711905f8912e5af474ca8b78d077447d8f3918997fecbf26943ff3cbb \
|
--hash=sha256:f7c5d642db47376a0cc130f0de6d055056e010debdaf0707cd2b0fc7e7ef30ea \
|
||||||
--hash=sha256:e5012e5cc2ac628177eaac0e83d622b2dd499e28253d4107a08ecc59ede3fc2c \
|
--hash=sha256:fcb6d9afb1b6208b4c712af0dafdc650f518836065df0d4fb1d800f5d6773db2 \
|
||||||
--hash=sha256:eb4f18589d196a4cbe5290b435d135dee96567e07c2b2d43b5c4621b6501531a
|
--hash=sha256:fcd2572dd4519e8a6642b733cd3a8cfc1ef94bafd0c1ceed9c94fe736cb65b6a
|
||||||
# via
|
# via
|
||||||
# manageprojects
|
# manageprojects
|
||||||
# pyinventory-ynh (pyproject.toml)
|
# pyinventory-ynh (pyproject.toml)
|
||||||
|
@ -694,7 +684,6 @@ packaging==23.2 \
|
||||||
# dparse
|
# dparse
|
||||||
# gunicorn
|
# gunicorn
|
||||||
# pyproject-api
|
# pyproject-api
|
||||||
# pytest
|
|
||||||
# safety
|
# safety
|
||||||
# tox
|
# tox
|
||||||
pathspec==0.11.2 \
|
pathspec==0.11.2 \
|
||||||
|
@ -765,9 +754,9 @@ pkginfo==1.9.6 \
|
||||||
--hash=sha256:4b7a555a6d5a22169fcc9cf7bfd78d296b0361adad412a346c1226849af5e546 \
|
--hash=sha256:4b7a555a6d5a22169fcc9cf7bfd78d296b0361adad412a346c1226849af5e546 \
|
||||||
--hash=sha256:8fd5896e8718a4372f0ea9cc9d96f6417c9b986e23a4d116dda26b62cc29d046
|
--hash=sha256:8fd5896e8718a4372f0ea9cc9d96f6417c9b986e23a4d116dda26b62cc29d046
|
||||||
# via twine
|
# via twine
|
||||||
platformdirs==3.11.0 \
|
platformdirs==4.0.0 \
|
||||||
--hash=sha256:cf8ee52a3afdb965072dcc652433e0c7e3e40cf5ea1477cd4b3b1d2eb75495b3 \
|
--hash=sha256:118c954d7e949b35437270383a3f2531e99dd93cf7ce4dc8340d3356d30f173b \
|
||||||
--hash=sha256:e9d171d00af68be50e9202731309c4e658fd8bc76f55c11c7dd760d023bda68e
|
--hash=sha256:cb633b2bcf10c51af60beb0ab06d2f1d69064b43abf4c185ca6b28865f3f9731
|
||||||
# via
|
# via
|
||||||
# black
|
# black
|
||||||
# tox
|
# tox
|
||||||
|
@ -775,9 +764,7 @@ platformdirs==3.11.0 \
|
||||||
pluggy==1.3.0 \
|
pluggy==1.3.0 \
|
||||||
--hash=sha256:cf61ae8f126ac6f7c451172cf30e3e43d3ca77615509771b3a984a0730651e12 \
|
--hash=sha256:cf61ae8f126ac6f7c451172cf30e3e43d3ca77615509771b3a984a0730651e12 \
|
||||||
--hash=sha256:d89c696a773f8bd377d18e5ecda92b7a3793cbe66c87060a6fb58c7b6e1061f7
|
--hash=sha256:d89c696a773f8bd377d18e5ecda92b7a3793cbe66c87060a6fb58c7b6e1061f7
|
||||||
# via
|
# via tox
|
||||||
# pytest
|
|
||||||
# tox
|
|
||||||
pprintpp==0.4.0 \
|
pprintpp==0.4.0 \
|
||||||
--hash=sha256:b6b4dcdd0c0c0d75e4d7b2f21a9e933e5b2ce62b26e1a54537f9651ae5a5c01d \
|
--hash=sha256:b6b4dcdd0c0c0d75e4d7b2f21a9e933e5b2ce62b26e1a54537f9651ae5a5c01d \
|
||||||
--hash=sha256:ea826108e2c7f49dc6d66c752973c3fc9749142a798d6b254e1e301cfdbc6403
|
--hash=sha256:ea826108e2c7f49dc6d66c752973c3fc9749142a798d6b254e1e301cfdbc6403
|
||||||
|
@ -815,9 +802,9 @@ pyflakes==3.1.0 \
|
||||||
# flake8
|
# flake8
|
||||||
# manageprojects
|
# manageprojects
|
||||||
# pyinventory-ynh (pyproject.toml)
|
# pyinventory-ynh (pyproject.toml)
|
||||||
pygments==2.16.1 \
|
pygments==2.17.2 \
|
||||||
--hash=sha256:13fc09fa63bc8d8671a6d247e1eb303c4b343eaee81d861f3404db2935653692 \
|
--hash=sha256:b27c2826c47d0f3219f29554824c30c5e8945175d888647acd804ddd04af846c \
|
||||||
--hash=sha256:1daff0494820c69bc8941e407aa20f577374ee88364ee10a98fdbe0aece96e29
|
--hash=sha256:da46cec9fd2de5be3a8a784f434e4c4ab670b4ff54d605c4c2717e9d49c4c367
|
||||||
# via
|
# via
|
||||||
# darker
|
# darker
|
||||||
# readme-renderer
|
# readme-renderer
|
||||||
|
@ -834,21 +821,6 @@ pyproject-hooks==1.0.0 \
|
||||||
--hash=sha256:283c11acd6b928d2f6a7c73fa0d01cb2bdc5f07c57a2eeb6e83d5e56b97976f8 \
|
--hash=sha256:283c11acd6b928d2f6a7c73fa0d01cb2bdc5f07c57a2eeb6e83d5e56b97976f8 \
|
||||||
--hash=sha256:f271b298b97f5955d53fb12b72c1fb1948c22c1a6b70b315c54cedaca0264ef5
|
--hash=sha256:f271b298b97f5955d53fb12b72c1fb1948c22c1a6b70b315c54cedaca0264ef5
|
||||||
# via build
|
# via build
|
||||||
pytest==7.4.3 \
|
|
||||||
--hash=sha256:0d009c083ea859a71b76adf7c1d502e4bc170b80a8ef002da5806527b9591fac \
|
|
||||||
--hash=sha256:d989d136982de4e3b29dabcc838ad581c64e8ed52c11fbe86ddebd9da0818cd5
|
|
||||||
# via
|
|
||||||
# pyinventory-ynh (pyproject.toml)
|
|
||||||
# pytest-cov
|
|
||||||
# pytest-django
|
|
||||||
pytest-cov==4.1.0 \
|
|
||||||
--hash=sha256:3904b13dfbfec47f003b8e77fd5b589cd11904a21ddf1ab38a64f204d6a10ef6 \
|
|
||||||
--hash=sha256:6ba70b9e97e69fcc3fb45bfeab2d0a138fb65c4d0d6a41ef33983ad114be8c3a
|
|
||||||
# via pyinventory-ynh (pyproject.toml)
|
|
||||||
pytest-django==4.7.0 \
|
|
||||||
--hash=sha256:4e1c79d5261ade2dd58d91208017cd8f62cb4710b56e012ecd361d15d5d662a2 \
|
|
||||||
--hash=sha256:92d6fd46b1d79b54fb6b060bbb39428073396cec717d5f2e122a990d4b6aa5e8
|
|
||||||
# via pyinventory-ynh (pyproject.toml)
|
|
||||||
python-dateutil==2.8.2 \
|
python-dateutil==2.8.2 \
|
||||||
--hash=sha256:0123cacc1627ae19ddf3c27a5de5bd67ee4586fbdd6440d9748f8abb483d3e86 \
|
--hash=sha256:0123cacc1627ae19ddf3c27a5de5bd67ee4586fbdd6440d9748f8abb483d3e86 \
|
||||||
--hash=sha256:961d03dc3453ebbc59dbdea9e4e11c5651520a876d0f4db161e8674aae935da9
|
--hash=sha256:961d03dc3453ebbc59dbdea9e4e11c5651520a876d0f4db161e8674aae935da9
|
||||||
|
@ -951,9 +923,9 @@ rfc3986==2.0.0 \
|
||||||
--hash=sha256:50b1502b60e289cb37883f3dfd34532b8873c7de9f49bb546641ce9cbd256ebd \
|
--hash=sha256:50b1502b60e289cb37883f3dfd34532b8873c7de9f49bb546641ce9cbd256ebd \
|
||||||
--hash=sha256:97aacf9dbd4bfd829baad6e6309fa6573aaf1be3f6fa735c8ab05e46cecb261c
|
--hash=sha256:97aacf9dbd4bfd829baad6e6309fa6573aaf1be3f6fa735c8ab05e46cecb261c
|
||||||
# via twine
|
# via twine
|
||||||
rich==13.6.0 \
|
rich==13.7.0 \
|
||||||
--hash=sha256:2b38e2fe9ca72c9a00170a1a2d20c63c790d0e10ef1fe35eba76e1e7b1d7d245 \
|
--hash=sha256:5cb5123b5cf9ee70584244246816e9114227e0b98ad9176eede6ad54bf5403fa \
|
||||||
--hash=sha256:5c14d22737e6d5084ef4771b62d5d4363165b403455a30a1c8ca39dc7b644bef
|
--hash=sha256:6da14c108c4866ee9520bbffa71f6fe3962e193b7da68720583850cd4548e235
|
||||||
# via
|
# via
|
||||||
# cli-base-utilities
|
# cli-base-utilities
|
||||||
# cookiecutter
|
# cookiecutter
|
||||||
|
@ -1052,6 +1024,10 @@ tablib[html,ods,xls,xlsx,yaml]==3.5.0 \
|
||||||
# via
|
# via
|
||||||
# django-import-export
|
# django-import-export
|
||||||
# tablib
|
# tablib
|
||||||
|
tblib==3.0.0 \
|
||||||
|
--hash=sha256:80a6c77e59b55e83911e1e607c649836a69c103963c5f28a46cbeef44acf8129 \
|
||||||
|
--hash=sha256:93622790a0a29e04f0346458face1e144dc4d32f493714c6c3dff82a4adb77e6
|
||||||
|
# via pyinventory-ynh (pyproject.toml)
|
||||||
text-unidecode==1.3 \
|
text-unidecode==1.3 \
|
||||||
--hash=sha256:1311f10e8b895935241623731c2ba64f4c455287888b18189350b67134a822e8 \
|
--hash=sha256:1311f10e8b895935241623731c2ba64f4c455287888b18189350b67134a822e8 \
|
||||||
--hash=sha256:bad6603bb14d279193107714b288be206cac565dfa49aa5b105294dd5c4aab93
|
--hash=sha256:bad6603bb14d279193107714b288be206cac565dfa49aa5b105294dd5c4aab93
|
||||||
|
@ -1070,9 +1046,9 @@ tomli==2.0.1 \
|
||||||
# via
|
# via
|
||||||
# flynt
|
# flynt
|
||||||
# pyinventory-ynh (pyproject.toml)
|
# pyinventory-ynh (pyproject.toml)
|
||||||
tomlkit==0.12.2 \
|
tomlkit==0.12.3 \
|
||||||
--hash=sha256:df32fab589a81f0d7dc525a4267b6d7a64ee99619cbd1eeb0fae32c1dd426977 \
|
--hash=sha256:75baf5012d06501f07bee5bf8e801b9f343e7aac5a92581f20f80ce632e6b5a4 \
|
||||||
--hash=sha256:eeea7ac7563faeab0a1ed8fe12c2e5a51c61f933f2502f7e9db0241a65163ad0
|
--hash=sha256:b0a645a9156dc7cb5d3a1f0d4bab66db287fcb8e0430bdd4664a095ea16414ba
|
||||||
# via
|
# via
|
||||||
# cli-base-utilities
|
# cli-base-utilities
|
||||||
# manageprojects
|
# manageprojects
|
||||||
|
@ -1094,23 +1070,23 @@ typing-extensions==4.8.0 \
|
||||||
# via
|
# via
|
||||||
# mypy
|
# mypy
|
||||||
# rich-click
|
# rich-click
|
||||||
urllib3==2.0.7 \
|
urllib3==2.1.0 \
|
||||||
--hash=sha256:c97dfde1f7bd43a71c8d2a58e369e9b2bf692d1334ea9f9cae55add7d0dd0f84 \
|
--hash=sha256:55901e917a5896a349ff771be919f8bd99aff50b79fe58fec595eb37bbc56bb3 \
|
||||||
--hash=sha256:fdb6d215c776278489906c2f8916e6e7d4f5a9b602ccbcfdf7f016fc8da0596e
|
--hash=sha256:df7aa8afb0148fa78488e7899b2c59b5f4ffcfa82e6c54ccb9dd37c1d7b52d54
|
||||||
# via
|
# via
|
||||||
# requests
|
# requests
|
||||||
# twine
|
# twine
|
||||||
virtualenv==20.24.6 \
|
virtualenv==20.24.7 \
|
||||||
--hash=sha256:02ece4f56fbf939dbbc33c0715159951d6bf14aaf5457b092e4548e1382455af \
|
--hash=sha256:69050ffb42419c91f6c1284a7b24e0475d793447e35929b488bf6a0aade39353 \
|
||||||
--hash=sha256:520d056652454c5098a00c0f073611ccbea4c79089331f60bf9d7ba247bb7381
|
--hash=sha256:a18b3fd0314ca59a2e9f4b556819ed07183b3e9a3702ecfe213f593d44f7b3fd
|
||||||
# via tox
|
# via tox
|
||||||
webencodings==0.5.1 \
|
webencodings==0.5.1 \
|
||||||
--hash=sha256:a0af1213f3c2226497a97e2b3aa01a7e4bee4f403f95be16fc9acd2947514a78 \
|
--hash=sha256:a0af1213f3c2226497a97e2b3aa01a7e4bee4f403f95be16fc9acd2947514a78 \
|
||||||
--hash=sha256:b36a1c245f2d304965eb4e0a82848379241dc04b865afcc4aab16748587e1923
|
--hash=sha256:b36a1c245f2d304965eb4e0a82848379241dc04b865afcc4aab16748587e1923
|
||||||
# via bleach
|
# via bleach
|
||||||
wheel==0.41.3 \
|
wheel==0.42.0 \
|
||||||
--hash=sha256:488609bc63a29322326e05560731bf7bfea8e48ad646e1f5e40d366607de0942 \
|
--hash=sha256:177f9c9b0d45c47873b619f5b650346d632cdc35fb5e4d25058e09c9e581433d \
|
||||||
--hash=sha256:4d4987ce51a49370ea65c0bfd2234e8ce80a12780820d9dc462597a6e60d0841
|
--hash=sha256:c45be39f7882c9d34243236f2d63cbd58039e360f85d0913425fbd7ceea617a8
|
||||||
# via pip-tools
|
# via pip-tools
|
||||||
xlrd==2.0.1 \
|
xlrd==2.0.1 \
|
||||||
--hash=sha256:6a33ee89877bd9abc1158129f6e94be74e2679636b8a205b43b85206c3f0bbdd \
|
--hash=sha256:6a33ee89877bd9abc1158129f6e94be74e2679636b8a205b43b85206c3f0bbdd \
|
||||||
|
@ -1130,9 +1106,9 @@ pip==23.3.1 \
|
||||||
--hash=sha256:1fcaa041308d01f14575f6d0d2ea4b75a3e2871fe4f9c694976f908768e14174 \
|
--hash=sha256:1fcaa041308d01f14575f6d0d2ea4b75a3e2871fe4f9c694976f908768e14174 \
|
||||||
--hash=sha256:55eb67bb6171d37447e82213be585b75fe2b12b359e993773aca4de9247a052b
|
--hash=sha256:55eb67bb6171d37447e82213be585b75fe2b12b359e993773aca4de9247a052b
|
||||||
# via pip-tools
|
# via pip-tools
|
||||||
setuptools==68.2.2 \
|
setuptools==69.0.2 \
|
||||||
--hash=sha256:4ac1475276d2f1c48684874089fefcd83bd7162ddaafb81fac866ba0db282a87 \
|
--hash=sha256:1e8fdff6797d3865f37397be788a4e3cba233608e9b509382a2777d25ebde7f2 \
|
||||||
--hash=sha256:b454a35605876da60632df1a60f736524eb73cc47bbc9f3f1ef1b644de74fd2a
|
--hash=sha256:735896e78a4742605974de002ac60562d286fa8051a7e2299445e8e8fbb01aa6
|
||||||
# via
|
# via
|
||||||
# django-axes
|
# django-axes
|
||||||
# pip-tools
|
# pip-tools
|
||||||
|
|
|
@ -13,7 +13,7 @@ __YNH_CURRENT_HOST__=${ynh_current_host}
|
||||||
#=================================================
|
#=================================================
|
||||||
|
|
||||||
# 'debug_enabled' -> '__DEBUG_ENABLED__' -> settings.DEBUG
|
# 'debug_enabled' -> '__DEBUG_ENABLED__' -> settings.DEBUG
|
||||||
debug_enabled="NO" # "YES" or "NO" string
|
debug_enabled="0" # "1" or "0" string
|
||||||
|
|
||||||
# 'log_level' -> '__LOG_LEVEL__' -> settings.LOG_LEVEL
|
# 'log_level' -> '__LOG_LEVEL__' -> settings.LOG_LEVEL
|
||||||
log_level="WARNING"
|
log_level="WARNING"
|
||||||
|
|
|
@ -1,43 +0,0 @@
|
||||||
"""
|
|
||||||
Special pytest init:
|
|
||||||
|
|
||||||
- Build a "local_test" YunoHost installation
|
|
||||||
- init Django with this local test installation
|
|
||||||
|
|
||||||
So the pytests will run against this local test installation
|
|
||||||
"""
|
|
||||||
import os
|
|
||||||
import sys
|
|
||||||
from pathlib import Path
|
|
||||||
|
|
||||||
import django
|
|
||||||
from django_yunohost_integration.local_test import CreateResults, create_local_test
|
|
||||||
|
|
||||||
|
|
||||||
BASE_PATH = Path(__file__).parent.parent
|
|
||||||
|
|
||||||
os.environ['DJANGO_SETTINGS_MODULE'] = 'settings'
|
|
||||||
|
|
||||||
|
|
||||||
def pytest_configure():
|
|
||||||
print('Compile YunoHost files...')
|
|
||||||
result: CreateResults = create_local_test(
|
|
||||||
django_settings_path=BASE_PATH / 'conf' / 'settings.py',
|
|
||||||
destination=BASE_PATH / 'local_test',
|
|
||||||
runserver=False,
|
|
||||||
extra_replacements={
|
|
||||||
'__DEBUG_ENABLED__': 'NO', # "YES" or "NO" string
|
|
||||||
'__LOG_LEVEL__': 'INFO',
|
|
||||||
'__ADMIN_EMAIL__': 'foo-bar@test.tld',
|
|
||||||
'__DEFAULT_FROM_EMAIL__': 'django_app@test.tld',
|
|
||||||
},
|
|
||||||
)
|
|
||||||
print('Local test files created:')
|
|
||||||
print(result)
|
|
||||||
|
|
||||||
os.chdir(result.data_dir_path)
|
|
||||||
data_dir = str(result.data_dir_path)
|
|
||||||
if data_dir not in sys.path:
|
|
||||||
sys.path.insert(0, data_dir)
|
|
||||||
|
|
||||||
django.setup()
|
|
|
@ -1,92 +0,0 @@
|
||||||
<div id="container">
|
|
||||||
<!-- Header -->
|
|
||||||
<div id="header">
|
|
||||||
<div id="branding">
|
|
||||||
<h1 id="site-name">
|
|
||||||
<a href="/app_path/">
|
|
||||||
PyInventory v0.19.3
|
|
||||||
</a>
|
|
||||||
</h1>
|
|
||||||
</div>
|
|
||||||
<div id="user-tools">
|
|
||||||
Welcome,
|
|
||||||
<strong>
|
|
||||||
test
|
|
||||||
</strong>
|
|
||||||
.
|
|
||||||
<a href="/">
|
|
||||||
View site
|
|
||||||
</a>
|
|
||||||
/
|
|
||||||
<a href="/app_path/password_change/">
|
|
||||||
Change password
|
|
||||||
</a>
|
|
||||||
/
|
|
||||||
<form action="/app_path/logout/" id="logout-form" method="post">
|
|
||||||
MockedCsrfTokenNode
|
|
||||||
<button type="submit">
|
|
||||||
Log out
|
|
||||||
</button>
|
|
||||||
</form>
|
|
||||||
<button class="theme-toggle">
|
|
||||||
<div class="visually-hidden theme-label-when-auto">
|
|
||||||
Toggle theme (current theme: auto)
|
|
||||||
</div>
|
|
||||||
<div class="visually-hidden theme-label-when-light">
|
|
||||||
Toggle theme (current theme: light)
|
|
||||||
</div>
|
|
||||||
<div class="visually-hidden theme-label-when-dark">
|
|
||||||
Toggle theme (current theme: dark)
|
|
||||||
</div>
|
|
||||||
<svg aria-hidden="true" class="theme-icon-when-auto">
|
|
||||||
<use xlink:href="#icon-auto">
|
|
||||||
</use>
|
|
||||||
</svg>
|
|
||||||
<svg aria-hidden="true" class="theme-icon-when-dark">
|
|
||||||
<use xlink:href="#icon-moon">
|
|
||||||
</use>
|
|
||||||
</svg>
|
|
||||||
<svg aria-hidden="true" class="theme-icon-when-light">
|
|
||||||
<use xlink:href="#icon-sun">
|
|
||||||
</use>
|
|
||||||
</svg>
|
|
||||||
</button>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<!-- END Header -->
|
|
||||||
<div class="main" id="main">
|
|
||||||
<div class="content" id="content-start" tabindex="-1">
|
|
||||||
<!-- Content -->
|
|
||||||
<div class="colMS" id="content">
|
|
||||||
<h1>
|
|
||||||
Site administration
|
|
||||||
</h1>
|
|
||||||
<div id="content-main">
|
|
||||||
<p>
|
|
||||||
You don’t have permission to view or edit anything.
|
|
||||||
</p>
|
|
||||||
</div>
|
|
||||||
<div id="content-related">
|
|
||||||
<div class="module" id="recent-actions-module">
|
|
||||||
<h2>
|
|
||||||
Recent actions
|
|
||||||
</h2>
|
|
||||||
<h3>
|
|
||||||
My actions
|
|
||||||
</h3>
|
|
||||||
<p>
|
|
||||||
None available
|
|
||||||
</p>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<br class="clear"/>
|
|
||||||
</div>
|
|
||||||
<!-- END Content -->
|
|
||||||
<div id="footer">
|
|
||||||
<a href="https://github.com/jedie/PyInventory">
|
|
||||||
https://github.com/jedie/PyInventory
|
|
||||||
</a>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
|
@ -1,108 +0,0 @@
|
||||||
import os
|
|
||||||
from pathlib import Path
|
|
||||||
from unittest import TestCase
|
|
||||||
|
|
||||||
|
|
||||||
try:
|
|
||||||
import tomllib # New in Python 3.11
|
|
||||||
except ImportError:
|
|
||||||
import tomli as tomllib
|
|
||||||
|
|
||||||
from bx_django_utils.filename import clean_filename
|
|
||||||
from bx_py_utils.path import assert_is_dir, assert_is_file
|
|
||||||
from django_tools.unittest_utils.project_setup import check_editor_config
|
|
||||||
from django_yunohost_integration.test_utils import assert_project_version
|
|
||||||
|
|
||||||
from inventory import __version__ as inventory_version
|
|
||||||
from pyinventory_ynh import __version__ as pyinventory_ynh_version
|
|
||||||
|
|
||||||
|
|
||||||
PACKAGE_ROOT = Path(__file__).parent.parent
|
|
||||||
|
|
||||||
|
|
||||||
def assert_file_contains_string(file_path, string):
|
|
||||||
with file_path.open('r') as f:
|
|
||||||
for line in f:
|
|
||||||
if string in line:
|
|
||||||
return
|
|
||||||
raise AssertionError(f'File {file_path} does not contain {string!r} !')
|
|
||||||
|
|
||||||
|
|
||||||
def test_version():
|
|
||||||
assert inventory_version in pyinventory_ynh_version, f'{inventory_version!r} not in {pyinventory_ynh_version!r}'
|
|
||||||
|
|
||||||
assert '+ynh' in pyinventory_ynh_version, f'{pyinventory_ynh_version!r} does not contain "+ynh"'
|
|
||||||
|
|
||||||
# pyproject.toml needs a PEP 440 conform version and used "+ynh"
|
|
||||||
# the YunoHost syntax is: "~ynh", just "convert this:
|
|
||||||
manifest_version = pyinventory_ynh_version.replace('+', '~')
|
|
||||||
|
|
||||||
assert_file_contains_string(
|
|
||||||
file_path=Path(PACKAGE_ROOT, 'manifest.toml'),
|
|
||||||
string=f'version = "{manifest_version}"',
|
|
||||||
)
|
|
||||||
|
|
||||||
if 'GITHUB_ACTION' not in os.environ:
|
|
||||||
# Github has a rate-limiting... So don't fetch the API if we run as GitHub action
|
|
||||||
assert_project_version(
|
|
||||||
current_version=inventory_version,
|
|
||||||
github_project_url='https://github.com/jedie/PyInventory',
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def test_screenshot_filenames():
|
|
||||||
"""
|
|
||||||
https://forum.yunohost.org/t/yunohost-bot-cant-handle-spaces-in-screenshots/19483
|
|
||||||
"""
|
|
||||||
screenshot_path = PACKAGE_ROOT / 'doc' / 'screenshots'
|
|
||||||
assert_is_dir(screenshot_path)
|
|
||||||
renamed = []
|
|
||||||
for file_path in screenshot_path.iterdir():
|
|
||||||
file_name = file_path.name
|
|
||||||
if file_name.startswith('.'):
|
|
||||||
continue
|
|
||||||
cleaned_name = clean_filename(file_name)
|
|
||||||
if cleaned_name != file_name:
|
|
||||||
new_path = file_path.with_name(cleaned_name)
|
|
||||||
file_path.rename(new_path)
|
|
||||||
renamed.append(f'{file_name!r} renamed to {cleaned_name!r}')
|
|
||||||
assert not renamed, f'Bad screenshots file names found: {", ".join(renamed)}'
|
|
||||||
|
|
||||||
|
|
||||||
def test_check_editor_config():
|
|
||||||
check_editor_config(package_root=PACKAGE_ROOT)
|
|
||||||
|
|
||||||
|
|
||||||
class ManifestTestCase(TestCase):
|
|
||||||
def test_manifest_toml(self):
|
|
||||||
manifest_path = PACKAGE_ROOT / 'manifest.toml'
|
|
||||||
assert_is_file(manifest_path)
|
|
||||||
|
|
||||||
cfg = tomllib.loads(manifest_path.read_text(encoding='UTF-8'))
|
|
||||||
|
|
||||||
self.assertEqual(cfg['packaging_format'], 2)
|
|
||||||
self.assertEqual(
|
|
||||||
set(cfg['install'].keys()),
|
|
||||||
{
|
|
||||||
'admin',
|
|
||||||
'admin_email',
|
|
||||||
'debug_enabled',
|
|
||||||
'default_from_email',
|
|
||||||
'domain',
|
|
||||||
'init_main_permission',
|
|
||||||
'log_level',
|
|
||||||
'path',
|
|
||||||
},
|
|
||||||
)
|
|
||||||
self.assertEqual(
|
|
||||||
set(cfg['resources'].keys()),
|
|
||||||
{
|
|
||||||
'apt',
|
|
||||||
'data_dir',
|
|
||||||
'database',
|
|
||||||
'install_dir',
|
|
||||||
'permissions',
|
|
||||||
'ports',
|
|
||||||
'system_user',
|
|
||||||
},
|
|
||||||
)
|
|
|
@ -1,8 +0,0 @@
|
||||||
from unittest.case import TestCase
|
|
||||||
|
|
||||||
from django_yunohost_integration.test_utils import generate_basic_auth
|
|
||||||
|
|
||||||
|
|
||||||
class TestUtilsTestCase(TestCase):
|
|
||||||
def test_generate_basic_auth(self):
|
|
||||||
assert generate_basic_auth(username='test', password='test123') == 'basic dGVzdDp0ZXN0MTIz'
|
|
Loading…
Reference in a new issue