passlib issueshttps://foss.heptapod.net/python-libs/passlib/-/issues2024-03-14T22:14:46Zhttps://foss.heptapod.net/python-libs/passlib/-/issues/190Warning about missing `bcrypt.__about__`, after upgrading bcrypt from 4.0.1 t...2024-03-14T22:14:46ZTommaso ComparinWarning about missing `bcrypt.__about__`, after upgrading bcrypt from 4.0.1 to 4.1.1When upgrading the `bcrypt` dependency from 4.0.1 to 4.1.1 (note that 4.1.0 was yanked), the `bcrypt.__about__.__version__` attribute is not available any more, while `bcrypt.__version__` remains. See following test with python 3.10.12, ...When upgrading the `bcrypt` dependency from 4.0.1 to 4.1.1 (note that 4.1.0 was yanked), the `bcrypt.__about__.__version__` attribute is not available any more, while `bcrypt.__version__` remains. See following test with python 3.10.12, on Ubuntu 22.04.3:
```plaintext
$ pip install bcrypt==4.0.1
Collecting bcrypt==4.0.1
Using cached bcrypt-4.0.1-cp36-abi3-manylinux_2_28_x86_64.whl (593 kB)
Installing collected packages: bcrypt
Attempting uninstall: bcrypt
Found existing installation: bcrypt 4.1.1
Uninstalling bcrypt-4.1.1:
Successfully uninstalled bcrypt-4.1.1
Successfully installed bcrypt-4.0.1
$ python -c "import bcrypt; print(bcrypt.__about__.__version__)"
4.0.1
$ python -c "import bcrypt; print(bcrypt.__version__)"
4.0.1
$ pip install bcrypt==4.1.1
Collecting bcrypt==4.1.1
Using cached bcrypt-4.1.1-cp37-abi3-manylinux_2_28_x86_64.whl (699 kB)
Installing collected packages: bcrypt
Attempting uninstall: bcrypt
Found existing installation: bcrypt 4.0.1
Uninstalling bcrypt-4.0.1:
Successfully uninstalled bcrypt-4.0.1
Successfully installed bcrypt-4.1.1
$ python -c "import bcrypt; print(bcrypt.__about__.__version__)"
Traceback (most recent call last):
File "<string>", line 1, in <module>
AttributeError: module 'bcrypt' has no attribute '__about__'
$ python -c "import bcrypt; print(bcrypt.__version__)"
4.1.1
```
---
`passlib` tries to access the `__about__.__version__` attribute in the following block in `handlers/bcrypt.py` (ref https://foss.heptapod.net/python-libs/passlib/-/blob/branch/stable/passlib/handlers/bcrypt.py):
```python
try:
version = _bcrypt.__about__.__version__
except:
log.warning("(trapped) error reading bcrypt version", exc_info=True)
version = '<unknown>'
```
and then raises a warning:
```plaintext
Python 3.10.12 (main, Nov 20 2023, 15:14:05) [GCC 11.4.0] on linux
Type "help", "copyright", "credits" or "license" for more information.
>>> from passlib.hash import bcrypt
>>> h = bcrypt.hash("password")
(trapped) error reading bcrypt version
Traceback (most recent call last):
File "/home/tommaso/Fractal/fractal-server/tests/data/example_server_startup/venv/lib/python3.10/site-packages/passlib/handlers/bcrypt.py", line 620, in _load_backend_mixin
version = _bcrypt.__about__.__version__
AttributeError: module 'bcrypt' has no attribute '__about__'
```
---
EDIT: here is the relevant bcrypt commit: https://github.com/pyca/bcrypt/commit/7939bef883a6ede5691134a250087c066e371bc01.7.5https://foss.heptapod.net/python-libs/passlib/-/issues/185Python 3.12 has deprecated pkg_resources2024-03-14T22:13:50ZReK_Python 3.12 has deprecated pkg_resourcesAs of Python 3.12, the pkg_resources module fails to import. You can see this in the automated pre-tests of my tools which relies on this library: https://github.com/ReK42/passhash/actions/runs/5721796256/job/15503907977?pr=2
```python
...As of Python 3.12, the pkg_resources module fails to import. You can see this in the automated pre-tests of my tools which relies on this library: https://github.com/ReK42/passhash/actions/runs/5721796256/job/15503907977?pr=2
```python
Traceback (most recent call last):
File "/opt/hostedtoolcache/Python/3.12.0-beta.4/x64/bin/passhash", line 5, in <module>
from passhash import main
File "/opt/hostedtoolcache/Python/3.12.0-beta.4/x64/lib/python3.12/site-packages/passhash/__init__.py", line 16, in <module>
from passhash.passhash import ALGORITHMS, main
File "/opt/hostedtoolcache/Python/3.12.0-beta.4/x64/lib/python3.12/site-packages/passhash/passhash.py", line 10, in <module>
from passlib import pwd
File "/opt/hostedtoolcache/Python/3.12.0-beta.4/x64/lib/python3.12/site-packages/passlib/pwd.py", line 16, in <module>
import pkg_resources
ModuleNotFoundError: No module named 'pkg_resources'
Error: Process completed with exit code 1.
```1.7.5https://foss.heptapod.net/python-libs/passlib/-/issues/132Unrecognized blowfish hash2024-03-09T20:08:45ZÉloi RivardUnrecognized blowfish hashHi
It looks like `custom_app_context.verify` does not recognize blowfish passwords generated with `bcrypt`.
```python
>>> from passlib.hash import bcrypt
>>> from passlib.apps import custom_app_context
>>> password = "foobar"
>>> cust...Hi
It looks like `custom_app_context.verify` does not recognize blowfish passwords generated with `bcrypt`.
```python
>>> from passlib.hash import bcrypt
>>> from passlib.apps import custom_app_context
>>> password = "foobar"
>>> custom_app_context.verify(password, bcrypt.hash(password))
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "/home/eloi/env/lib/python3.7/site-packages/passlib/context.py", line 2343, in verify
record = self._get_or_identify_record(hash, scheme, category)
File "/home/eloi/env/lib/python3.7/site-packages/passlib/context.py", line 2031, in _get_or_identify_record
return self._identify_record(hash, category)
File "/home/eloi/env/lib/python3.7/site-packages/passlib/context.py", line 1132, in identify_record
raise exc.UnknownHashError("hash could not be identified")
passlib.exc.UnknownHashError: hash could not be identified
hash could not be identified
```
Reading the README, I would have expected this piece of code to work. Am I missing something or is there a real bug here?
Éloihttps://foss.heptapod.net/python-libs/passlib/-/issues/187Maintenance status?2024-03-09T15:18:03ZThibaut BarrèreMaintenance status?I am opening this issue to discuss the maintenance status of `passlib`!
(please note that I am also myself an open-source maintainer and I don't feel entitled to anything here, just trying to share some useful info & concerns).
I am a ...I am opening this issue to discuss the maintenance status of `passlib`!
(please note that I am also myself an open-source maintainer and I don't feel entitled to anything here, just trying to share some useful info & concerns).
I am a newcomer to `passlib` and only using it via Ansible, because it is required by default on Mac if one uses Ansible:
https://github.com/ansible/ansible/blob/f22231de203450128dbfcd3277799d759d861abd/lib/ansible/utils/encrypt.py#L94-L95
EDIT: :warning: soon **all** users Ansible will likely rely on `passlib` (see https://github.com/ansible/ansible/issues/81949#issuecomment-1766693535).
I am a bit concerned about its maintenance status, due to various hints:
- the last public release was done 3 years ago
- no recent commits
And also issues like:
- #186
- #185
- #148
The fact that it is used in Ansible (something largely used) is also a concern!
It took me a bit of time to find the right place where discussion still occur (via [this comment](https://github.com/glic3rinu/passlib/issues/55#issuecomment-1487631731)).
Is @eli-collins still maintaining the library? Has someone taken over?
Happy to help out, by the way.
Thanks!
### Impacted projects
* ansible https://github.com/ansible/ansible/issues/81949
* fast-api-users https://github.com/fastapi-users/fastapi-users/issues/1301
Please comment or edit so that we can measure the impact!https://foss.heptapod.net/python-libs/passlib/-/issues/148'crypt' is deprecated and slated for removal in Python 3.132024-03-09T15:03:13ZJeremy Stanley'crypt' is deprecated and slated for removal in Python 3.13https://peps.python.org/pep-0594/#crypt
Since passlib leverages the crypt module specifically in order to handle old and insecure password hashes, it may make sense to forklift the code from stdlib into the project or collaborate on cre...https://peps.python.org/pep-0594/#crypt
Since passlib leverages the crypt module specifically in order to handle old and insecure password hashes, it may make sense to forklift the code from stdlib into the project or collaborate on creating an external fork which it can consume for Python 3.13 and later.1.8https://foss.heptapod.net/python-libs/passlib/-/issues/87Add support for Cisco PBKDF2 and Scrypt hashes2023-12-01T16:08:59ZBitbucket ImporterAdd support for Cisco PBKDF2 and Scrypt hashes*Created originally on Bitbucket by Anonymous*
Cisco IOS added "type 8" and "type 9" hashes (based pbkdf2-sha256, and scrypt, respectively). Cisco ASA 9.5 added a separate "pbkdf2" hash (based on sha512 based).
Shouldn't be too har...*Created originally on Bitbucket by Anonymous*
Cisco IOS added "type 8" and "type 9" hashes (based pbkdf2-sha256, and scrypt, respectively). Cisco ASA 9.5 added a separate "pbkdf2" hash (based on sha512 based).
Shouldn't be too hard to add support for these. Mainly need to gather together some test vectors, figure out the edge cases (max password size, max parameter sizes, etc). Already have a few accumulated for cisco_asa_pbkdf2.Wishlisthttps://foss.heptapod.net/python-libs/passlib/-/issues/189Misguided salt normalization logic for bcrypt2023-11-27T17:15:44ZDominique QuatravauxMisguided salt normalization logic for bcryptUsing version 1.7.4 of passlib, the following script:
```
from passlib.handlers.bcrypt import bcrypt
from base64 import b64decode
settings = {'ident': '2b', 'rounds': 12, 'salt': 'Aejoo1theicoquo9waeT6O'}
hasher = bcrypt.using(setting...Using version 1.7.4 of passlib, the following script:
```
from passlib.handlers.bcrypt import bcrypt
from base64 import b64decode
settings = {'ident': '2b', 'rounds': 12, 'salt': 'Aejoo1theicoquo9waeT6O'}
hasher = bcrypt.using(settings)
print(hasher.hash('passw0rd'))
```
produces the following stack trace:
```
Traceback (most recent call last):
File "/Users/quatrava/Dev/tmp/test.py", line 8, in <module>
print(hasher.hash('passw0rd'))
^^^^^^^^^^^^^^^^^^^^^^^
File "/Users/quatrava/Dev/ops/go-epfl/go-ops/ansible-deps-cache/python-libs/lib/python/site-packages/passlib/utils/handlers.py", line 779, in hash
self.checksum = self._calc_checksum(secret)
^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/Users/quatrava/Dev/ops/go-epfl/go-ops/ansible-deps-cache/python-libs/lib/python/site-packages/passlib/handlers/bcrypt.py", line 591, in _calc_checksum
self._stub_requires_backend()
File "/Users/quatrava/Dev/ops/go-epfl/go-ops/ansible-deps-cache/python-libs/lib/python/site-packages/passlib/utils/handlers.py", line 2254, in _stub_requires_backend
cls.set_backend()
File "/Users/quatrava/Dev/ops/go-epfl/go-ops/ansible-deps-cache/python-libs/lib/python/site-packages/passlib/utils/handlers.py", line 2156, in set_backend
return owner.set_backend(name, dryrun=dryrun)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/Users/quatrava/Dev/ops/go-epfl/go-ops/ansible-deps-cache/python-libs/lib/python/site-packages/passlib/utils/handlers.py", line 2163, in set_backend
return cls.set_backend(name, dryrun=dryrun)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/Users/quatrava/Dev/ops/go-epfl/go-ops/ansible-deps-cache/python-libs/lib/python/site-packages/passlib/utils/handlers.py", line 2188, in set_backend
cls._set_backend(name, dryrun)
File "/Users/quatrava/Dev/ops/go-epfl/go-ops/ansible-deps-cache/python-libs/lib/python/site-packages/passlib/utils/handlers.py", line 2311, in _set_backend
super(SubclassBackendMixin, cls)._set_backend(name, dryrun)
File "/Users/quatrava/Dev/ops/go-epfl/go-ops/ansible-deps-cache/python-libs/lib/python/site-packages/passlib/utils/handlers.py", line 2224, in _set_backend
ok = loader(**kwds)
^^^^^^^^^^^^^^
File "/Users/quatrava/Dev/ops/go-epfl/go-ops/ansible-deps-cache/python-libs/lib/python/site-packages/passlib/handlers/bcrypt.py", line 745, in _load_backend_mixin
return mixin_cls._finalize_backend_mixin(name, dryrun)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/Users/quatrava/Dev/ops/go-epfl/go-ops/ansible-deps-cache/python-libs/lib/python/site-packages/passlib/handlers/bcrypt.py", line 403, in _finalize_backend_mixin
result = safe_verify("test", test_hash_20)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/Users/quatrava/Dev/ops/go-epfl/go-ops/ansible-deps-cache/python-libs/lib/python/site-packages/passlib/handlers/bcrypt.py", line 303, in safe_verify
return verify(secret, hash)
^^^^^^^^^^^^^^^^^^^^
File "/Users/quatrava/Dev/ops/go-epfl/go-ops/ansible-deps-cache/python-libs/lib/python/site-packages/passlib/utils/handlers.py", line 792, in verify
return consteq(self._calc_checksum(secret), chk)
^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/Users/quatrava/Dev/ops/go-epfl/go-ops/ansible-deps-cache/python-libs/lib/python/site-packages/passlib/handlers/bcrypt.py", line 762, in _calc_checksum_raw
hash = _pybcrypt.hashpw(secret, config)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
TypeError: argument 'salt': 'str' object cannot be converted to 'PyBytes'
```https://foss.heptapod.net/python-libs/passlib/-/issues/186ugettext_noop deprecated in Django 3.02023-09-28T16:20:49ZPaolo Lapointe-Miriellougettext_noop deprecated in Django 3.0I rarely submit issues for repositories, sorry if I'm doing it wrong :) I believe the use of `ugettext_noop` in [passlib/ext/django/utils.py (line 995)](https://foss.heptapod.net/search?search=ugettext_noop&nav_source=navbar&project_id=1...I rarely submit issues for repositories, sorry if I'm doing it wrong :) I believe the use of `ugettext_noop` in [passlib/ext/django/utils.py (line 995)](https://foss.heptapod.net/search?search=ugettext_noop&nav_source=navbar&project_id=142&group_id=379&search_code=true&repository_ref=branch%2Fstable) is causing issues with the django-hashers-passlib package because `ugettext_noop` was deprecated in Django 3.0. The proper function should be `gettext_noop` if I'm not mistaken.https://foss.heptapod.net/python-libs/passlib/-/issues/137Did passlib supported Apple M1 chip?2023-09-28T13:49:33Zleonlee723Did passlib supported Apple M1 chip?I have developed a project with FastAPI and passlib. Code is as below:
pwd_context = CryptContext(schemes=["sha256_crypt", "des_crypt"], deprecated="auto")
But when I debugged this code, as below error show on the console
passlib.exc.Unk...I have developed a project with FastAPI and passlib. Code is as below:
pwd_context = CryptContext(schemes=["sha256_crypt", "des_crypt"], deprecated="auto")
But when I debugged this code, as below error show on the console
passlib.exc.UnknownHashError: hash could not be identified
My laptop is Apple MacBook pro m1, so did passlib supported Apple M1 chip?https://foss.heptapod.net/python-libs/passlib/-/issues/152misleading rounds param for sha521_crypt2022-12-30T20:41:01ZSer@finmisleading rounds param for sha521_cryptHi,
I do the following:
```python
#!/usr/bin/env python3
import secrets
import passlib.hash
from pprint import pprint
SALT_LEN=8
crypter = passlib.hash.sha512_crypt(salt=secrets.token_hex(SALT_LEN), rounds=5000)
result = crypter.has...Hi,
I do the following:
```python
#!/usr/bin/env python3
import secrets
import passlib.hash
from pprint import pprint
SALT_LEN=8
crypter = passlib.hash.sha512_crypt(salt=secrets.token_hex(SALT_LEN), rounds=5000)
result = crypter.hash('test')
pprint(result)
pprint(crypter.verify('test', result))
```
and the result I got:
```python
'$6$rounds=656000$wq48b6CZ8H/cPgDV$HRu3fPUwkfSK4JHXriKxwotNw/I/ul2Gq76mU5e7w0PSaxePwn77NK/GuuQvCaKmOeLMfDUbAGajQStVyPnMT.'
True
```
please note the fact that I specify rounds as 5000 and I'm getting rounds=656000 in hashed output. That wouldn't bother me as this is default value, however, when I omit rounds param I'm getting:
```python
Traceback (most recent call last):
File "./generate_pass.py", line 9, in <module>
crypter = passlib.hash.sha512_crypt(salt=secrets.token_hex(SALT_LEN)) # , rounds=5000)
File "/venv/lib/python3.10/site-packages/passlib/handlers/sha2_crypt.py", line 281, in __init__
super(_SHA2_Common, self).__init__(**kwds)
File "/venv/lib/python3.10/site-packages/passlib/utils/handlers.py", line 1801, in __init__
raise TypeError("no rounds specified")
TypeError: no rounds specified
```
my questions:
1. is it possible to generate hash with 5000 rounds? if yes - how?
2. why rounds param is mandatory while it is ignored during hash generation?
Thanks in advance for Your help and Big Thanks for Your work on the library
Ser@finhttps://foss.heptapod.net/python-libs/passlib/-/issues/151Argon2 hash() method will not accept a `salt` kwarg2022-12-03T00:11:37ZPatrickArgon2 hash() method will not accept a `salt` kwargOn the [documentation page](https://passlib.readthedocs.io/en/stable/lib/passlib.hash.argon2.html#passlib.hash.argon2) for Argon2 it seems like the hash function should accept a passed salt (rather than autogenerating one).
However, whe...On the [documentation page](https://passlib.readthedocs.io/en/stable/lib/passlib.hash.argon2.html#passlib.hash.argon2) for Argon2 it seems like the hash function should accept a passed salt (rather than autogenerating one).
However, when I try to do something like `pwd_context.hash("blah", salt="hi")` (where `pwd_context` is a `CryptContext` set to Argon2), I get a `TypeError: hash() got an unexpected keyword argument 'salt'`.
I took a look at what I [think the code is](https://foss.heptapod.net/python-libs/passlib/-/blob/branch/stable/passlib/handlers/argon2.py#L737) that is preventing the salt `kwd` and it looks like it is not setup to accept a `salt` kwd.
I would advocate that the `hash()` method for Argon2 should be able to accept that kwd.https://foss.heptapod.net/python-libs/passlib/-/issues/13514 tests fails with "django.core.exceptions.ImproperlyConfigured: The SECRET...2022-11-17T15:15:22ZMatěj Cepl14 tests fails with "django.core.exceptions.ImproperlyConfigured: The SECRET_KEY setting must not be empty."When packaging passlib for openSUSE, we run the test suite and 14 tests fail:
```
[ 171s] __________________ DjangoBehaviorTest.test_available_schemes ___________________
[ 171s]
[ 171s] self = <passlib.tests.test_ext_django.DjangoBe...When packaging passlib for openSUSE, we run the test suite and 14 tests fail:
```
[ 171s] __________________ DjangoBehaviorTest.test_available_schemes ___________________
[ 171s]
[ 171s] self = <passlib.tests.test_ext_django.DjangoBehaviorTest testMethod=test_available_schemes>
[ 171s]
[ 171s] def test_available_schemes(self):
[ 171s] """
[ 171s] run a bunch of subtests for each hasher available in the default django setup
[ 171s] (as determined by reading self.context)
[ 171s] """
[ 171s] for scheme in self.context.schemes():
[ 171s] with self.subTest(scheme=scheme):
[ 171s] > self._do_test_available_scheme(scheme)
[ 171s]
[ 171s] passlib/tests/test_ext_django.py:707:
[ 171s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 171s] passlib/tests/test_ext_django.py:790: in _do_test_available_scheme
[ 171s] self.assert_valid_password(user, hash)
[ 171s] passlib/tests/test_ext_django.py:435: in assert_valid_password
[ 171s] self.assertEqual(user.password, hash)
[ 171s] E AssertionError: 'pbkdf2_sha256$260000$d1TkjOgyD4m7GhqxQI0bkW$JZeVGBR5eYRI4cA1lG[22 chars]q6s=' != 'pbkdf2_sha256$260000$WNiU6tO1moWh$l5YsPqDWWnDf0TBZ38H3Hu5hpG9l8AOODt9I8SDSfWk='
[ 171s] E - pbkdf2_sha256$260000$d1TkjOgyD4m7GhqxQI0bkW$JZeVGBR5eYRI4cA1lGM90vuyr8rt9R9emYoFC/p/q6s=
[ 171s] E + pbkdf2_sha256$260000$WNiU6tO1moWh$l5YsPqDWWnDf0TBZ38H3Hu5hpG9l8AOODt9I8SDSfWk=
[ 171s] ------------------------------ Captured log call -------------------------------
[ 171s] WARNING passlib.tests.test_ext_django.DjangoBehaviorTest.test_available_schemes:utils.py:684 subtest failed: (scheme='django_pbkdf2_sha256'): AssertionError: "'pbkdf2_sha256$260000$d1TkjOgyD4m7GhqxQI0bkW$JZeVGBR5eYRI4cA1lG[22 chars]q6s=' != 'pbkdf2_sha256$260000$WNiU6tO1moWh$l5YsPqDWWnDf0TBZ38H3Hu5hpG9l8AOODt9I8SDSfWk='\n- pbkdf2_sha256$260000$d1TkjOgyD4m7GhqxQI0bkW$JZeVGBR5eYRI4cA1lGM90vuyr8rt9R9emYoFC/p/q6s=\n+ pbkdf2_sha256$260000$WNiU6tO1moWh$l5YsPqDWWnDf0TBZ38H3Hu5hpG9l8AOODt9I8SDSfWk=\n"
[ 171s] _________________ ExtensionBehaviorTest.test_available_schemes _________________
[ 171s]
[ 171s] self = <passlib.tests.test_ext_django.ExtensionBehaviorTest testMethod=test_available_schemes>
[ 171s]
[ 171s] def setUp(self):
[ 171s] super(ExtensionBehaviorTest, self).setUp()
[ 171s]
[ 171s] # always load extension before each test
[ 171s] > self.load_extension(PASSLIB_CONFIG=self.config)
[ 171s]
[ 171s] passlib/tests/test_ext_django.py:850:
[ 171s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 171s] passlib/tests/test_ext_django.py:313: in load_extension
[ 171s] import passlib.ext.django.models
[ 171s] passlib/ext/django/models.py:32: in <module>
[ 171s] adapter.load_model()
[ 171s] passlib/ext/django/utils.py:792: in load_model
[ 171s] self.install_patch()
[ 171s] passlib/ext/django/utils.py:736: in install_patch
[ 171s] manager.patch(target, value)
[ 171s] passlib/ext/django/utils.py:1194: in patch
[ 171s] current = self._get_path(path)
[ 171s] passlib/ext/django/utils.py:1153: in _get_path
[ 171s] obj, attr = self._import_path(key)
[ 171s] passlib/ext/django/utils.py:1138: in _import_path
[ 171s] obj = __import__(name, fromlist=[attr], level=0)
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/forms.py:11: in <module>
[ 171s] from django.contrib.auth.tokens import default_token_generator
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:117: in <module>
[ 171s] default_token_generator = PasswordResetTokenGenerator()
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:18: in __init__
[ 171s] self.secret = self.secret or settings.SECRET_KEY
[ 171s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 171s]
[ 171s] self = <LazySettings "None">, name = 'SECRET_KEY'
[ 171s]
[ 171s] def __getattr__(self, name):
[ 171s] """Return the value of a setting and cache it in self.__dict__."""
[ 171s] if self._wrapped is empty:
[ 171s] self._setup(name)
[ 171s] val = getattr(self._wrapped, name)
[ 171s]
[ 171s] # Special case some settings which require further modification.
[ 171s] # This is done here for performance reasons so the modified value is cached.
[ 171s] if name in {'MEDIA_URL', 'STATIC_URL'} and val is not None:
[ 171s] val = self._add_script_prefix(val)
[ 171s] elif name == 'SECRET_KEY' and not val:
[ 171s] > raise ImproperlyConfigured("The SECRET_KEY setting must not be empty.")
[ 171s] E django.core.exceptions.ImproperlyConfigured: The SECRET_KEY setting must not be empty.
[ 171s]
[ 171s] /usr/lib/python3.6/site-packages/django/conf/__init__.py:90: ImproperlyConfigured
[ 171s] ------------------------------ Captured log call -------------------------------
[ 171s] WARNING passlib.ext.django.utils.DjangoContextAdapter:utils.py:771 reverting partial monkeypatching of django...
[ 171s] _________________ ExtensionBehaviorTest.test_default_algorithm _________________
[ 171s]
[ 171s] self = <passlib.tests.test_ext_django.ExtensionBehaviorTest testMethod=test_default_algorithm>
[ 171s]
[ 171s] def setUp(self):
[ 171s] super(ExtensionBehaviorTest, self).setUp()
[ 171s]
[ 171s] # always load extension before each test
[ 171s] > self.load_extension(PASSLIB_CONFIG=self.config)
[ 171s]
[ 171s] passlib/tests/test_ext_django.py:850:
[ 171s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 171s] passlib/tests/test_ext_django.py:313: in load_extension
[ 171s] import passlib.ext.django.models
[ 171s] passlib/ext/django/models.py:32: in <module>
[ 171s] adapter.load_model()
[ 171s] passlib/ext/django/utils.py:792: in load_model
[ 171s] self.install_patch()
[ 171s] passlib/ext/django/utils.py:736: in install_patch
[ 171s] manager.patch(target, value)
[ 171s] passlib/ext/django/utils.py:1194: in patch
[ 171s] current = self._get_path(path)
[ 171s] passlib/ext/django/utils.py:1153: in _get_path
[ 171s] obj, attr = self._import_path(key)
[ 171s] passlib/ext/django/utils.py:1138: in _import_path
[ 171s] obj = __import__(name, fromlist=[attr], level=0)
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/forms.py:11: in <module>
[ 171s] from django.contrib.auth.tokens import default_token_generator
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:117: in <module>
[ 171s] default_token_generator = PasswordResetTokenGenerator()
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:18: in __init__
[ 171s] self.secret = self.secret or settings.SECRET_KEY
[ 171s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 171s]
[ 171s] self = <LazySettings "None">, name = 'SECRET_KEY'
[ 171s]
[ 171s] def __getattr__(self, name):
[ 171s] """Return the value of a setting and cache it in self.__dict__."""
[ 171s] if self._wrapped is empty:
[ 171s] self._setup(name)
[ 171s] val = getattr(self._wrapped, name)
[ 171s]
[ 171s] # Special case some settings which require further modification.
[ 171s] # This is done here for performance reasons so the modified value is cached.
[ 171s] if name in {'MEDIA_URL', 'STATIC_URL'} and val is not None:
[ 171s] val = self._add_script_prefix(val)
[ 171s] elif name == 'SECRET_KEY' and not val:
[ 171s] > raise ImproperlyConfigured("The SECRET_KEY setting must not be empty.")
[ 171s] E django.core.exceptions.ImproperlyConfigured: The SECRET_KEY setting must not be empty.
[ 171s]
[ 171s] /usr/lib/python3.6/site-packages/django/conf/__init__.py:90: ImproperlyConfigured
[ 171s] ------------------------------ Captured log call -------------------------------
[ 171s] WARNING passlib.ext.django.utils.DjangoContextAdapter:utils.py:771 reverting partial monkeypatching of django...
[ 171s] _________________ ExtensionBehaviorTest.test_empty_hash_value __________________
[ 171s]
[ 171s] self = <passlib.tests.test_ext_django.ExtensionBehaviorTest testMethod=test_empty_hash_value>
[ 171s]
[ 171s] def setUp(self):
[ 171s] super(ExtensionBehaviorTest, self).setUp()
[ 171s]
[ 171s] # always load extension before each test
[ 171s] > self.load_extension(PASSLIB_CONFIG=self.config)
[ 171s]
[ 171s] passlib/tests/test_ext_django.py:850:
[ 171s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 171s] passlib/tests/test_ext_django.py:313: in load_extension
[ 171s] import passlib.ext.django.models
[ 171s] passlib/ext/django/models.py:32: in <module>
[ 171s] adapter.load_model()
[ 171s] passlib/ext/django/utils.py:792: in load_model
[ 171s] self.install_patch()
[ 171s] passlib/ext/django/utils.py:736: in install_patch
[ 171s] manager.patch(target, value)
[ 171s] passlib/ext/django/utils.py:1194: in patch
[ 171s] current = self._get_path(path)
[ 171s] passlib/ext/django/utils.py:1153: in _get_path
[ 171s] obj, attr = self._import_path(key)
[ 171s] passlib/ext/django/utils.py:1138: in _import_path
[ 171s] obj = __import__(name, fromlist=[attr], level=0)
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/forms.py:11: in <module>
[ 171s] from django.contrib.auth.tokens import default_token_generator
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:117: in <module>
[ 171s] default_token_generator = PasswordResetTokenGenerator()
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:18: in __init__
[ 171s] self.secret = self.secret or settings.SECRET_KEY
[ 171s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 171s]
[ 171s] self = <LazySettings "None">, name = 'SECRET_KEY'
[ 171s]
[ 171s] def __getattr__(self, name):
[ 171s] """Return the value of a setting and cache it in self.__dict__."""
[ 171s] if self._wrapped is empty:
[ 171s] self._setup(name)
[ 171s] val = getattr(self._wrapped, name)
[ 171s]
[ 171s] # Special case some settings which require further modification.
[ 171s] # This is done here for performance reasons so the modified value is cached.
[ 171s] if name in {'MEDIA_URL', 'STATIC_URL'} and val is not None:
[ 171s] val = self._add_script_prefix(val)
[ 171s] elif name == 'SECRET_KEY' and not val:
[ 171s] > raise ImproperlyConfigured("The SECRET_KEY setting must not be empty.")
[ 171s] E django.core.exceptions.ImproperlyConfigured: The SECRET_KEY setting must not be empty.
[ 171s]
[ 171s] /usr/lib/python3.6/site-packages/django/conf/__init__.py:90: ImproperlyConfigured
[ 171s] ------------------------------ Captured log call -------------------------------
[ 171s] WARNING passlib.ext.django.utils.DjangoContextAdapter:utils.py:771 reverting partial monkeypatching of django...
[ 171s] __________________ ExtensionBehaviorTest.test_empty_password ___________________
[ 171s]
[ 171s] self = <passlib.tests.test_ext_django.ExtensionBehaviorTest testMethod=test_empty_password>
[ 171s]
[ 171s] def setUp(self):
[ 171s] super(ExtensionBehaviorTest, self).setUp()
[ 171s]
[ 171s] # always load extension before each test
[ 171s] > self.load_extension(PASSLIB_CONFIG=self.config)
[ 171s]
[ 171s] passlib/tests/test_ext_django.py:850:
[ 171s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 171s] passlib/tests/test_ext_django.py:313: in load_extension
[ 171s] import passlib.ext.django.models
[ 171s] passlib/ext/django/models.py:32: in <module>
[ 171s] adapter.load_model()
[ 171s] passlib/ext/django/utils.py:792: in load_model
[ 171s] self.install_patch()
[ 171s] passlib/ext/django/utils.py:736: in install_patch
[ 171s] manager.patch(target, value)
[ 171s] passlib/ext/django/utils.py:1194: in patch
[ 171s] current = self._get_path(path)
[ 171s] passlib/ext/django/utils.py:1153: in _get_path
[ 171s] obj, attr = self._import_path(key)
[ 171s] passlib/ext/django/utils.py:1138: in _import_path
[ 171s] obj = __import__(name, fromlist=[attr], level=0)
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/forms.py:11: in <module>
[ 171s] from django.contrib.auth.tokens import default_token_generator
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:117: in <module>
[ 171s] default_token_generator = PasswordResetTokenGenerator()
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:18: in __init__
[ 171s] self.secret = self.secret or settings.SECRET_KEY
[ 171s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 171s]
[ 171s] self = <LazySettings "None">, name = 'SECRET_KEY'
[ 171s]
[ 171s] def __getattr__(self, name):
[ 171s] """Return the value of a setting and cache it in self.__dict__."""
[ 171s] if self._wrapped is empty:
[ 171s] self._setup(name)
[ 171s] val = getattr(self._wrapped, name)
[ 171s]
[ 171s] # Special case some settings which require further modification.
[ 171s] # This is done here for performance reasons so the modified value is cached.
[ 171s] if name in {'MEDIA_URL', 'STATIC_URL'} and val is not None:
[ 171s] val = self._add_script_prefix(val)
[ 171s] elif name == 'SECRET_KEY' and not val:
[ 171s] > raise ImproperlyConfigured("The SECRET_KEY setting must not be empty.")
[ 171s] E django.core.exceptions.ImproperlyConfigured: The SECRET_KEY setting must not be empty.
[ 171s]
[ 171s] /usr/lib/python3.6/site-packages/django/conf/__init__.py:90: ImproperlyConfigured
[ 171s] ------------------------------ Captured log call -------------------------------
[ 171s] WARNING passlib.ext.django.utils.DjangoContextAdapter:utils.py:771 reverting partial monkeypatching of django...
[ 171s] _________________ ExtensionBehaviorTest.test_extension_config __________________
[ 171s]
[ 171s] self = <passlib.tests.test_ext_django.ExtensionBehaviorTest testMethod=test_extension_config>
[ 171s]
[ 171s] def setUp(self):
[ 171s] super(ExtensionBehaviorTest, self).setUp()
[ 171s]
[ 171s] # always load extension before each test
[ 171s] > self.load_extension(PASSLIB_CONFIG=self.config)
[ 171s]
[ 171s] passlib/tests/test_ext_django.py:850:
[ 171s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 171s] passlib/tests/test_ext_django.py:313: in load_extension
[ 171s] import passlib.ext.django.models
[ 171s] passlib/ext/django/models.py:32: in <module>
[ 171s] adapter.load_model()
[ 171s] passlib/ext/django/utils.py:792: in load_model
[ 171s] self.install_patch()
[ 171s] passlib/ext/django/utils.py:736: in install_patch
[ 171s] manager.patch(target, value)
[ 171s] passlib/ext/django/utils.py:1194: in patch
[ 171s] current = self._get_path(path)
[ 171s] passlib/ext/django/utils.py:1153: in _get_path
[ 171s] obj, attr = self._import_path(key)
[ 171s] passlib/ext/django/utils.py:1138: in _import_path
[ 171s] obj = __import__(name, fromlist=[attr], level=0)
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/forms.py:11: in <module>
[ 171s] from django.contrib.auth.tokens import default_token_generator
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:117: in <module>
[ 171s] default_token_generator = PasswordResetTokenGenerator()
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:18: in __init__
[ 171s] self.secret = self.secret or settings.SECRET_KEY
[ 171s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 171s]
[ 171s] self = <LazySettings "None">, name = 'SECRET_KEY'
[ 171s]
[ 171s] def __getattr__(self, name):
[ 171s] """Return the value of a setting and cache it in self.__dict__."""
[ 171s] if self._wrapped is empty:
[ 171s] self._setup(name)
[ 171s] val = getattr(self._wrapped, name)
[ 171s]
[ 171s] # Special case some settings which require further modification.
[ 171s] # This is done here for performance reasons so the modified value is cached.
[ 171s] if name in {'MEDIA_URL', 'STATIC_URL'} and val is not None:
[ 171s] val = self._add_script_prefix(val)
[ 171s] elif name == 'SECRET_KEY' and not val:
[ 171s] > raise ImproperlyConfigured("The SECRET_KEY setting must not be empty.")
[ 171s] E django.core.exceptions.ImproperlyConfigured: The SECRET_KEY setting must not be empty.
[ 171s]
[ 171s] /usr/lib/python3.6/site-packages/django/conf/__init__.py:90: ImproperlyConfigured
[ 171s] ------------------------------ Captured log call -------------------------------
[ 171s] WARNING passlib.ext.django.utils.DjangoContextAdapter:utils.py:771 reverting partial monkeypatching of django...
[ 171s] ________________ ExtensionBehaviorTest.test_invalid_hash_values ________________
[ 171s]
[ 171s] self = <passlib.tests.test_ext_django.ExtensionBehaviorTest testMethod=test_invalid_hash_values>
[ 171s]
[ 171s] def setUp(self):
[ 171s] super(ExtensionBehaviorTest, self).setUp()
[ 171s]
[ 171s] # always load extension before each test
[ 171s] > self.load_extension(PASSLIB_CONFIG=self.config)
[ 171s]
[ 171s] passlib/tests/test_ext_django.py:850:
[ 171s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 171s] passlib/tests/test_ext_django.py:313: in load_extension
[ 171s] import passlib.ext.django.models
[ 171s] passlib/ext/django/models.py:32: in <module>
[ 171s] adapter.load_model()
[ 171s] passlib/ext/django/utils.py:792: in load_model
[ 171s] self.install_patch()
[ 171s] passlib/ext/django/utils.py:736: in install_patch
[ 171s] manager.patch(target, value)
[ 171s] passlib/ext/django/utils.py:1194: in patch
[ 171s] current = self._get_path(path)
[ 171s] passlib/ext/django/utils.py:1153: in _get_path
[ 171s] obj, attr = self._import_path(key)
[ 171s] passlib/ext/django/utils.py:1138: in _import_path
[ 171s] obj = __import__(name, fromlist=[attr], level=0)
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/forms.py:11: in <module>
[ 171s] from django.contrib.auth.tokens import default_token_generator
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:117: in <module>
[ 171s] default_token_generator = PasswordResetTokenGenerator()
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:18: in __init__
[ 171s] self.secret = self.secret or settings.SECRET_KEY
[ 171s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 171s]
[ 171s] self = <LazySettings "None">, name = 'SECRET_KEY'
[ 171s]
[ 171s] def __getattr__(self, name):
[ 171s] """Return the value of a setting and cache it in self.__dict__."""
[ 171s] if self._wrapped is empty:
[ 171s] self._setup(name)
[ 171s] val = getattr(self._wrapped, name)
[ 171s]
[ 171s] # Special case some settings which require further modification.
[ 171s] # This is done here for performance reasons so the modified value is cached.
[ 171s] if name in {'MEDIA_URL', 'STATIC_URL'} and val is not None:
[ 171s] val = self._add_script_prefix(val)
[ 171s] elif name == 'SECRET_KEY' and not val:
[ 171s] > raise ImproperlyConfigured("The SECRET_KEY setting must not be empty.")
[ 171s] E django.core.exceptions.ImproperlyConfigured: The SECRET_KEY setting must not be empty.
[ 171s]
[ 171s] /usr/lib/python3.6/site-packages/django/conf/__init__.py:90: ImproperlyConfigured
[ 171s] ------------------------------ Captured log call -------------------------------
[ 171s] WARNING passlib.ext.django.utils.DjangoContextAdapter:utils.py:771 reverting partial monkeypatching of django...
[ 171s] __________________ ExtensionBehaviorTest.test_none_hash_value __________________
[ 171s]
[ 171s] self = <passlib.tests.test_ext_django.ExtensionBehaviorTest testMethod=test_none_hash_value>
[ 171s]
[ 171s] def setUp(self):
[ 171s] super(ExtensionBehaviorTest, self).setUp()
[ 171s]
[ 171s] # always load extension before each test
[ 171s] > self.load_extension(PASSLIB_CONFIG=self.config)
[ 171s]
[ 171s] passlib/tests/test_ext_django.py:850:
[ 171s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 171s] passlib/tests/test_ext_django.py:313: in load_extension
[ 171s] import passlib.ext.django.models
[ 171s] passlib/ext/django/models.py:32: in <module>
[ 171s] adapter.load_model()
[ 171s] passlib/ext/django/utils.py:792: in load_model
[ 171s] self.install_patch()
[ 171s] passlib/ext/django/utils.py:736: in install_patch
[ 171s] manager.patch(target, value)
[ 171s] passlib/ext/django/utils.py:1194: in patch
[ 171s] current = self._get_path(path)
[ 171s] passlib/ext/django/utils.py:1153: in _get_path
[ 171s] obj, attr = self._import_path(key)
[ 171s] passlib/ext/django/utils.py:1138: in _import_path
[ 171s] obj = __import__(name, fromlist=[attr], level=0)
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/forms.py:11: in <module>
[ 171s] from django.contrib.auth.tokens import default_token_generator
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:117: in <module>
[ 171s] default_token_generator = PasswordResetTokenGenerator()
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:18: in __init__
[ 171s] self.secret = self.secret or settings.SECRET_KEY
[ 171s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 171s]
[ 171s] self = <LazySettings "None">, name = 'SECRET_KEY'
[ 171s]
[ 171s] def __getattr__(self, name):
[ 171s] """Return the value of a setting and cache it in self.__dict__."""
[ 171s] if self._wrapped is empty:
[ 171s] self._setup(name)
[ 171s] val = getattr(self._wrapped, name)
[ 171s]
[ 171s] # Special case some settings which require further modification.
[ 171s] # This is done here for performance reasons so the modified value is cached.
[ 171s] if name in {'MEDIA_URL', 'STATIC_URL'} and val is not None:
[ 171s] val = self._add_script_prefix(val)
[ 171s] elif name == 'SECRET_KEY' and not val:
[ 171s] > raise ImproperlyConfigured("The SECRET_KEY setting must not be empty.")
[ 171s] E django.core.exceptions.ImproperlyConfigured: The SECRET_KEY setting must not be empty.
[ 171s]
[ 171s] /usr/lib/python3.6/site-packages/django/conf/__init__.py:90: ImproperlyConfigured
[ 171s] ------------------------------ Captured log call -------------------------------
[ 171s] WARNING passlib.ext.django.utils.DjangoContextAdapter:utils.py:771 reverting partial monkeypatching of django...
[ 171s] ___________________ ExtensionBehaviorTest.test_unusable_flag ___________________
[ 171s]
[ 171s] self = <passlib.tests.test_ext_django.ExtensionBehaviorTest testMethod=test_unusable_flag>
[ 171s]
[ 171s] def setUp(self):
[ 171s] super(ExtensionBehaviorTest, self).setUp()
[ 171s]
[ 171s] # always load extension before each test
[ 171s] > self.load_extension(PASSLIB_CONFIG=self.config)
[ 171s]
[ 171s] passlib/tests/test_ext_django.py:850:
[ 171s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 171s] passlib/tests/test_ext_django.py:313: in load_extension
[ 171s] import passlib.ext.django.models
[ 171s] passlib/ext/django/models.py:32: in <module>
[ 171s] adapter.load_model()
[ 171s] passlib/ext/django/utils.py:792: in load_model
[ 171s] self.install_patch()
[ 171s] passlib/ext/django/utils.py:736: in install_patch
[ 171s] manager.patch(target, value)
[ 171s] passlib/ext/django/utils.py:1194: in patch
[ 171s] current = self._get_path(path)
[ 171s] passlib/ext/django/utils.py:1153: in _get_path
[ 171s] obj, attr = self._import_path(key)
[ 171s] passlib/ext/django/utils.py:1138: in _import_path
[ 171s] obj = __import__(name, fromlist=[attr], level=0)
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/forms.py:11: in <module>
[ 171s] from django.contrib.auth.tokens import default_token_generator
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:117: in <module>
[ 171s] default_token_generator = PasswordResetTokenGenerator()
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:18: in __init__
[ 171s] self.secret = self.secret or settings.SECRET_KEY
[ 171s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 171s]
[ 171s] self = <LazySettings "None">, name = 'SECRET_KEY'
[ 171s]
[ 171s] def __getattr__(self, name):
[ 171s] """Return the value of a setting and cache it in self.__dict__."""
[ 171s] if self._wrapped is empty:
[ 171s] self._setup(name)
[ 171s] val = getattr(self._wrapped, name)
[ 171s]
[ 171s] # Special case some settings which require further modification.
[ 171s] # This is done here for performance reasons so the modified value is cached.
[ 171s] if name in {'MEDIA_URL', 'STATIC_URL'} and val is not None:
[ 171s] val = self._add_script_prefix(val)
[ 171s] elif name == 'SECRET_KEY' and not val:
[ 171s] > raise ImproperlyConfigured("The SECRET_KEY setting must not be empty.")
[ 171s] E django.core.exceptions.ImproperlyConfigured: The SECRET_KEY setting must not be empty.
[ 171s]
[ 171s] /usr/lib/python3.6/site-packages/django/conf/__init__.py:90: ImproperlyConfigured
[ 171s] ------------------------------ Captured log call -------------------------------
[ 171s] WARNING passlib.ext.django.utils.DjangoContextAdapter:utils.py:771 reverting partial monkeypatching of django...
[ 171s] __________________ DjangoExtensionTest.test_00_patch_control ___________________
[ 171s]
[ 171s] self = <passlib.tests.test_ext_django.DjangoExtensionTest testMethod=test_00_patch_control>
[ 171s]
[ 171s] def test_00_patch_control(self):
[ 171s] """test set_django_password_context patch/unpatch"""
[ 171s]
[ 171s] # check config="disabled"
[ 171s] self.load_extension(PASSLIB_CONFIG="disabled", check=False)
[ 171s] self.assert_unpatched()
[ 171s]
[ 171s] # check legacy config=None
[ 171s] with self.assertWarningList("PASSLIB_CONFIG=None is deprecated"):
[ 171s] self.load_extension(PASSLIB_CONFIG=None, check=False)
[ 171s] self.assert_unpatched()
[ 171s]
[ 171s] # try stock django 1.0 context
[ 171s] > self.load_extension(PASSLIB_CONFIG="django-1.0", check=False)
[ 171s]
[ 171s] passlib/tests/test_ext_django.py:884:
[ 171s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 171s] passlib/tests/test_ext_django.py:313: in load_extension
[ 171s] import passlib.ext.django.models
[ 171s] passlib/ext/django/models.py:32: in <module>
[ 171s] adapter.load_model()
[ 171s] passlib/ext/django/utils.py:792: in load_model
[ 171s] self.install_patch()
[ 171s] passlib/ext/django/utils.py:736: in install_patch
[ 171s] manager.patch(target, value)
[ 171s] passlib/ext/django/utils.py:1194: in patch
[ 171s] current = self._get_path(path)
[ 171s] passlib/ext/django/utils.py:1153: in _get_path
[ 171s] obj, attr = self._import_path(key)
[ 171s] passlib/ext/django/utils.py:1138: in _import_path
[ 171s] obj = __import__(name, fromlist=[attr], level=0)
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/forms.py:11: in <module>
[ 171s] from django.contrib.auth.tokens import default_token_generator
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:117: in <module>
[ 171s] default_token_generator = PasswordResetTokenGenerator()
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:18: in __init__
[ 171s] self.secret = self.secret or settings.SECRET_KEY
[ 171s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 171s]
[ 171s] self = <LazySettings "None">, name = 'SECRET_KEY'
[ 171s]
[ 171s] def __getattr__(self, name):
[ 171s] """Return the value of a setting and cache it in self.__dict__."""
[ 171s] if self._wrapped is empty:
[ 171s] self._setup(name)
[ 171s] val = getattr(self._wrapped, name)
[ 171s]
[ 171s] # Special case some settings which require further modification.
[ 171s] # This is done here for performance reasons so the modified value is cached.
[ 171s] if name in {'MEDIA_URL', 'STATIC_URL'} and val is not None:
[ 171s] val = self._add_script_prefix(val)
[ 171s] elif name == 'SECRET_KEY' and not val:
[ 171s] > raise ImproperlyConfigured("The SECRET_KEY setting must not be empty.")
[ 171s] E django.core.exceptions.ImproperlyConfigured: The SECRET_KEY setting must not be empty.
[ 171s]
[ 171s] /usr/lib/python3.6/site-packages/django/conf/__init__.py:90: ImproperlyConfigured
[ 171s] ------------------------------ Captured log call -------------------------------
[ 171s] WARNING passlib.ext.django.utils.DjangoContextAdapter:utils.py:771 reverting partial monkeypatching of django...
[ 171s] _______________ DjangoExtensionTest.test_01_overwrite_detection ________________
[ 171s]
[ 171s] self = <passlib.tests.test_ext_django.DjangoExtensionTest testMethod=test_01_overwrite_detection>
[ 171s]
[ 171s] def test_01_overwrite_detection(self):
[ 171s] """test detection of foreign monkeypatching"""
[ 171s] # NOTE: this sets things up, and spot checks two methods,
[ 171s] # this should be enough to verify patch manager is working.
[ 171s] # TODO: test unpatch behavior honors flag.
[ 171s]
[ 171s] # configure plugin to use sample context
[ 171s] config = "[passlib]\nschemes=des_crypt\n"
[ 171s] > self.load_extension(PASSLIB_CONFIG=config)
[ 171s]
[ 171s] passlib/tests/test_ext_django.py:905:
[ 171s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 171s] passlib/tests/test_ext_django.py:313: in load_extension
[ 171s] import passlib.ext.django.models
[ 171s] passlib/ext/django/models.py:32: in <module>
[ 171s] adapter.load_model()
[ 171s] passlib/ext/django/utils.py:792: in load_model
[ 171s] self.install_patch()
[ 171s] passlib/ext/django/utils.py:736: in install_patch
[ 171s] manager.patch(target, value)
[ 171s] passlib/ext/django/utils.py:1194: in patch
[ 171s] current = self._get_path(path)
[ 171s] passlib/ext/django/utils.py:1153: in _get_path
[ 171s] obj, attr = self._import_path(key)
[ 171s] passlib/ext/django/utils.py:1138: in _import_path
[ 171s] obj = __import__(name, fromlist=[attr], level=0)
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/forms.py:11: in <module>
[ 171s] from django.contrib.auth.tokens import default_token_generator
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:117: in <module>
[ 171s] default_token_generator = PasswordResetTokenGenerator()
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:18: in __init__
[ 171s] self.secret = self.secret or settings.SECRET_KEY
[ 171s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 171s]
[ 171s] self = <LazySettings "None">, name = 'SECRET_KEY'
[ 171s]
[ 171s] def __getattr__(self, name):
[ 171s] """Return the value of a setting and cache it in self.__dict__."""
[ 171s] if self._wrapped is empty:
[ 171s] self._setup(name)
[ 171s] val = getattr(self._wrapped, name)
[ 171s]
[ 171s] # Special case some settings which require further modification.
[ 171s] # This is done here for performance reasons so the modified value is cached.
[ 171s] if name in {'MEDIA_URL', 'STATIC_URL'} and val is not None:
[ 171s] val = self._add_script_prefix(val)
[ 171s] elif name == 'SECRET_KEY' and not val:
[ 171s] > raise ImproperlyConfigured("The SECRET_KEY setting must not be empty.")
[ 171s] E django.core.exceptions.ImproperlyConfigured: The SECRET_KEY setting must not be empty.
[ 171s]
[ 171s] /usr/lib/python3.6/site-packages/django/conf/__init__.py:90: ImproperlyConfigured
[ 171s] ------------------------------ Captured log call -------------------------------
[ 171s] WARNING passlib.ext.django.utils.DjangoContextAdapter:utils.py:771 reverting partial monkeypatching of django...
[ 171s] __________________ DjangoExtensionTest.test_12_config_presets __________________
[ 171s]
[ 171s] self = <passlib.tests.test_ext_django.DjangoExtensionTest testMethod=test_12_config_presets>
[ 171s]
[ 171s] def test_12_config_presets(self):
[ 171s] """test PASSLIB_CONFIG='<preset>'"""
[ 171s] # test django presets
[ 171s] > self.load_extension(PASSLIB_CONTEXT="django-default", check=False)
[ 171s]
[ 171s] passlib/tests/test_ext_django.py:989:
[ 171s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 171s] passlib/tests/test_ext_django.py:313: in load_extension
[ 171s] import passlib.ext.django.models
[ 171s] passlib/ext/django/models.py:32: in <module>
[ 171s] adapter.load_model()
[ 171s] passlib/ext/django/utils.py:792: in load_model
[ 171s] self.install_patch()
[ 171s] passlib/ext/django/utils.py:736: in install_patch
[ 171s] manager.patch(target, value)
[ 171s] passlib/ext/django/utils.py:1194: in patch
[ 171s] current = self._get_path(path)
[ 171s] passlib/ext/django/utils.py:1153: in _get_path
[ 171s] obj, attr = self._import_path(key)
[ 171s] passlib/ext/django/utils.py:1138: in _import_path
[ 171s] obj = __import__(name, fromlist=[attr], level=0)
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/forms.py:11: in <module>
[ 171s] from django.contrib.auth.tokens import default_token_generator
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:117: in <module>
[ 171s] default_token_generator = PasswordResetTokenGenerator()
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:18: in __init__
[ 171s] self.secret = self.secret or settings.SECRET_KEY
[ 171s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 171s]
[ 171s] self = <LazySettings "None">, name = 'SECRET_KEY'
[ 171s]
[ 171s] def __getattr__(self, name):
[ 171s] """Return the value of a setting and cache it in self.__dict__."""
[ 171s] if self._wrapped is empty:
[ 171s] self._setup(name)
[ 171s] val = getattr(self._wrapped, name)
[ 171s]
[ 171s] # Special case some settings which require further modification.
[ 171s] # This is done here for performance reasons so the modified value is cached.
[ 171s] if name in {'MEDIA_URL', 'STATIC_URL'} and val is not None:
[ 171s] val = self._add_script_prefix(val)
[ 171s] elif name == 'SECRET_KEY' and not val:
[ 171s] > raise ImproperlyConfigured("The SECRET_KEY setting must not be empty.")
[ 171s] E django.core.exceptions.ImproperlyConfigured: The SECRET_KEY setting must not be empty.
[ 171s]
[ 171s] /usr/lib/python3.6/site-packages/django/conf/__init__.py:90: ImproperlyConfigured
[ 171s] ------------------------------ Captured log call -------------------------------
[ 171s] WARNING passlib.ext.django.utils.DjangoContextAdapter:utils.py:771 reverting partial monkeypatching of django...
[ 171s] _________________ DjangoExtensionTest.test_13_config_defaults __________________
[ 171s]
[ 171s] self = <passlib.tests.test_ext_django.DjangoExtensionTest testMethod=test_13_config_defaults>
[ 171s]
[ 171s] def test_13_config_defaults(self):
[ 171s] """test PASSLIB_CONFIG default behavior"""
[ 171s] # check implicit default
[ 171s] from passlib.ext.django.utils import PASSLIB_DEFAULT
[ 171s] default = CryptContext.from_string(PASSLIB_DEFAULT)
[ 171s] > self.load_extension()
[ 171s]
[ 171s] passlib/tests/test_ext_django.py:1004:
[ 171s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 171s] passlib/tests/test_ext_django.py:313: in load_extension
[ 171s] import passlib.ext.django.models
[ 171s] passlib/ext/django/models.py:32: in <module>
[ 171s] adapter.load_model()
[ 171s] passlib/ext/django/utils.py:792: in load_model
[ 171s] self.install_patch()
[ 171s] passlib/ext/django/utils.py:736: in install_patch
[ 171s] manager.patch(target, value)
[ 171s] passlib/ext/django/utils.py:1194: in patch
[ 171s] current = self._get_path(path)
[ 171s] passlib/ext/django/utils.py:1153: in _get_path
[ 171s] obj, attr = self._import_path(key)
[ 171s] passlib/ext/django/utils.py:1138: in _import_path
[ 171s] obj = __import__(name, fromlist=[attr], level=0)
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/forms.py:11: in <module>
[ 171s] from django.contrib.auth.tokens import default_token_generator
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:117: in <module>
[ 171s] default_token_generator = PasswordResetTokenGenerator()
[ 171s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:18: in __init__
[ 172s] self.secret = self.secret or settings.SECRET_KEY
[ 172s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 172s]
[ 172s] self = <LazySettings "None">, name = 'SECRET_KEY'
[ 172s]
[ 172s] def __getattr__(self, name):
[ 172s] """Return the value of a setting and cache it in self.__dict__."""
[ 172s] if self._wrapped is empty:
[ 172s] self._setup(name)
[ 172s] val = getattr(self._wrapped, name)
[ 172s]
[ 172s] # Special case some settings which require further modification.
[ 172s] # This is done here for performance reasons so the modified value is cached.
[ 172s] if name in {'MEDIA_URL', 'STATIC_URL'} and val is not None:
[ 172s] val = self._add_script_prefix(val)
[ 172s] elif name == 'SECRET_KEY' and not val:
[ 172s] > raise ImproperlyConfigured("The SECRET_KEY setting must not be empty.")
[ 172s] E django.core.exceptions.ImproperlyConfigured: The SECRET_KEY setting must not be empty.
[ 172s]
[ 172s] /usr/lib/python3.6/site-packages/django/conf/__init__.py:90: ImproperlyConfigured
[ 172s] ------------------------------ Captured log call -------------------------------
[ 172s] WARNING passlib.ext.django.utils.DjangoContextAdapter:utils.py:771 reverting partial monkeypatching of django...
[ 172s] _________________ DjangoExtensionTest.test_21_category_setting _________________
[ 172s]
[ 172s] self = <passlib.tests.test_ext_django.DjangoExtensionTest testMethod=test_21_category_setting>
[ 172s]
[ 172s] def test_21_category_setting(self):
[ 172s] """test PASSLIB_GET_CATEGORY parameter"""
[ 172s] # define config where rounds can be used to detect category
[ 172s] config = dict(
[ 172s] schemes = ["sha256_crypt"],
[ 172s] sha256_crypt__default_rounds = 1000,
[ 172s] staff__sha256_crypt__default_rounds = 2000,
[ 172s] superuser__sha256_crypt__default_rounds = 3000,
[ 172s] )
[ 172s] from passlib.hash import sha256_crypt
[ 172s]
[ 172s] def run(**kwds):
[ 172s] """helper to take in user opts, return rounds used in password"""
[ 172s] user = FakeUser(**kwds)
[ 172s] user.set_password("stub")
[ 172s] return sha256_crypt.from_string(user.password).rounds
[ 172s]
[ 172s] # test default get_category
[ 172s] > self.load_extension(PASSLIB_CONFIG=config)
[ 172s]
[ 172s] passlib/tests/test_ext_django.py:1045:
[ 172s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 172s] passlib/tests/test_ext_django.py:313: in load_extension
[ 172s] import passlib.ext.django.models
[ 172s] passlib/ext/django/models.py:32: in <module>
[ 172s] adapter.load_model()
[ 172s] passlib/ext/django/utils.py:792: in load_model
[ 172s] self.install_patch()
[ 172s] passlib/ext/django/utils.py:736: in install_patch
[ 172s] manager.patch(target, value)
[ 172s] passlib/ext/django/utils.py:1194: in patch
[ 172s] current = self._get_path(path)
[ 172s] passlib/ext/django/utils.py:1153: in _get_path
[ 172s] obj, attr = self._import_path(key)
[ 172s] passlib/ext/django/utils.py:1138: in _import_path
[ 172s] obj = __import__(name, fromlist=[attr], level=0)
[ 172s] /usr/lib/python3.6/site-packages/django/contrib/auth/forms.py:11: in <module>
[ 172s] from django.contrib.auth.tokens import default_token_generator
[ 172s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:117: in <module>
[ 172s] default_token_generator = PasswordResetTokenGenerator()
[ 172s] /usr/lib/python3.6/site-packages/django/contrib/auth/tokens.py:18: in __init__
[ 172s] self.secret = self.secret or settings.SECRET_KEY
[ 172s] _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
[ 172s]
[ 172s] self = <LazySettings "None">, name = 'SECRET_KEY'
[ 172s]
[ 172s] def __getattr__(self, name):
[ 172s] """Return the value of a setting and cache it in self.__dict__."""
[ 172s] if self._wrapped is empty:
[ 172s] self._setup(name)
[ 172s] val = getattr(self._wrapped, name)
[ 172s]
[ 172s] # Special case some settings which require further modification.
[ 172s] # This is done here for performance reasons so the modified value is cached.
[ 172s] if name in {'MEDIA_URL', 'STATIC_URL'} and val is not None:
[ 172s] val = self._add_script_prefix(val)
[ 172s] elif name == 'SECRET_KEY' and not val:
[ 172s] > raise ImproperlyConfigured("The SECRET_KEY setting must not be empty.")
[ 172s] E django.core.exceptions.ImproperlyConfigured: The SECRET_KEY setting must not be empty.
[ 172s]
[ 172s] /usr/lib/python3.6/site-packages/django/conf/__init__.py:90: ImproperlyConfigured
[ 172s] ------------------------------ Captured log call -------------------------------
[ 172s] WARNING passlib.ext.django.utils.DjangoContextAdapter:utils.py:771 reverting partial monkeypatching of django...
[ 172s] =============================== warnings summary ===============================
[ 172s] passlib/tests/test_apache.py:210
[ 172s] /home/abuild/rpmbuild/BUILD/passlib-1.7.4/passlib/tests/test_apache.py:210: DeprecationWarning: invalid escape sequence \(
[ 172s] with self.assertWarningList("update\(\) is deprecated"):
[ 172s]
[ 172s] passlib/tests/test_apache.py:280
[ 172s] /home/abuild/rpmbuild/BUILD/passlib-1.7.4/passlib/tests/test_apache.py:280: DeprecationWarning: invalid escape sequence \(
[ 172s] with self.assertWarningList(["verify\(\) is deprecated"]*2):
[ 172s]
[ 172s] passlib/tests/test_apache.py:370
[ 172s] /home/abuild/rpmbuild/BUILD/passlib-1.7.4/passlib/tests/test_apache.py:370: DeprecationWarning: invalid escape sequence \(
[ 172s] with self.assertWarningList("find\(\) is deprecated"):
[ 172s]
[ 172s] passlib/tests/test_apache.py:606
[ 172s] /home/abuild/rpmbuild/BUILD/passlib-1.7.4/passlib/tests/test_apache.py:606: DeprecationWarning: invalid escape sequence \(
[ 172s] with self.assertWarningList("update\(\) is deprecated"):
[ 172s]
[ 172s] passlib/tests/test_apache.py:640
[ 172s] /home/abuild/rpmbuild/BUILD/passlib-1.7.4/passlib/tests/test_apache.py:640: DeprecationWarning: invalid escape sequence \(
[ 172s] with self.assertWarningList(["verify\(\) is deprecated"]*2):
[ 172s]
[ 172s] passlib/tests/test_apache.py:728
[ 172s] /home/abuild/rpmbuild/BUILD/passlib-1.7.4/passlib/tests/test_apache.py:728: DeprecationWarning: invalid escape sequence \(
[ 172s] with self.assertWarningList("find\(\) is deprecated"):
[ 172s]
[ 172s] passlib/tests/test_context_deprecated.py:554
[ 172s] /home/abuild/rpmbuild/BUILD/passlib-1.7.4/passlib/tests/test_context_deprecated.py:554: DeprecationWarning: invalid escape sequence \.
[ 172s] warnings.filterwarnings("ignore", ".*(CryptPolicy|context\.policy).*(has|have) been deprecated.*")
[ 172s]
[ 172s] passlib/tests/test_context_deprecated.py:707
[ 172s] /home/abuild/rpmbuild/BUILD/passlib-1.7.4/passlib/tests/test_context_deprecated.py:707: DeprecationWarning: invalid escape sequence \.
[ 172s] warnings.filterwarnings("ignore", ".*(CryptPolicy|context\.policy).*(has|have) been deprecated.*")
[ 172s]
[ 172s] passlib/tests/test_ext_django.py:916
[ 172s] /home/abuild/rpmbuild/BUILD/passlib-1.7.4/passlib/tests/test_ext_django.py:916: DeprecationWarning: invalid escape sequence \.
[ 172s] with self.assertWarningList("another library has patched.*User\.set_password"):
[ 172s]
[ 172s] passlib/tests/test_handlers.py:1523
[ 172s] /home/abuild/rpmbuild/BUILD/passlib-1.7.4/passlib/tests/test_handlers.py:1523: DeprecationWarning: invalid escape sequence \d
[ 172s] ("freebsd(9|1\d)|linux", True),
[ 172s]
[ 172s] passlib/tests/test_handlers.py:1761
[ 172s] /home/abuild/rpmbuild/BUILD/passlib-1.7.4/passlib/tests/test_handlers.py:1761: DeprecationWarning: invalid escape sequence \(
[ 172s] warnings.filterwarnings("ignore", "passing settings to .*.hash\(\) is deprecated")
[ 172s]
[ 172s] passlib/tests/test_utils.py:144
[ 172s] /home/abuild/rpmbuild/BUILD/passlib-1.7.4/passlib/tests/test_utils.py:144: DeprecationWarning: invalid escape sequence \(
[ 172s] warnings.filterwarnings("ignore", "The function.*generate_password\(\) is deprecated")
[ 172s]
[ 172s] passlib/tests/test_crypto_scrypt.py: 12 warnings
[ 172s] /home/abuild/rpmbuild/BUILD/passlib-1.7.4/passlib/crypto/scrypt/__init__.py:165: PasslibSecurityWarning: Using builtin scrypt backend, which is 100x slower than is required for adequate security. Installing scrypt support (via 'pip install scrypt') is strongly recommended
[ 172s] "is strongly recommended" % slowdown, exc.PasslibSecurityWarning)
[ 172s]
[ 172s] passlib/tests/test_ext_django.py::DjangoExtensionTest::test_02_handler_wrapper
[ 172s] /home/abuild/rpmbuild/BUILD/passlib-1.7.4/passlib/ext/django/utils.py:1000: RemovedInDjango40Warning: django.utils.translation.ugettext_noop() is deprecated in favor of django.utils.translation.gettext_noop().
[ 172s] (_('algorithm'), handler.name),
[ 172s]
[ 172s] passlib/tests/test_ext_django.py::DjangoExtensionTest::test_02_handler_wrapper
[ 172s] passlib/tests/test_ext_django.py::DjangoExtensionTest::test_02_handler_wrapper
[ 172s] passlib/tests/test_ext_django.py::DjangoExtensionTest::test_02_handler_wrapper
[ 172s] /home/abuild/rpmbuild/BUILD/passlib-1.7.4/passlib/ext/django/utils.py:1006: RemovedInDjango40Warning: django.utils.translation.ugettext_noop() is deprecated in favor of django.utils.translation.gettext_noop().
[ 172s] items.append((_(key), value))
[ 172s]
[ 172s] -- Docs: https://docs.pytest.org/en/stable/warnings.html
[ 172s] =========================== short test summary info ============================
[ 172s] SKIPPED [1] passlib/tests/test_crypto_scrypt.py:604: non-builtin backend is present
[ 172s] SKIPPED [1] passlib/tests/test_crypto_scrypt.py:615: higher priority backend present
[ 172s] SKIPPED [1] passlib/tests/test_ext_django.py:462: extension not loaded
[ 172s] SKIPPED [1] passlib/tests/test_ext_django_source.py:244: requires PASSLIB_TESTS_DJANGO_SOURCE_PATH to be set
[ 172s] SKIPPED [63] passlib/tests/utils.py:2004: handler doesn't derive from HasManyIdents
[ 172s] SKIPPED [63] passlib/tests/utils.py:2420: no alternate hashes provided
[ 172s] SKIPPED [58] passlib/tests/utils.py:2667: no samples present
[ 172s] SKIPPED [40] passlib/tests/utils.py:2445: no config strings provided
[ 172s] SKIPPED [43] passlib/tests/utils.py:2501: no malformed hashes provided
[ 172s] SKIPPED [68] passlib/tests/utils.py:2773: requires >= 'full' test mode
[ 172s] SKIPPED [3] passlib/tests/utils.py:3349: varied support on 'linux' platform (current host support = True)
[ 172s] SKIPPED [65] passlib/tests/utils.py:3079: not applicable
[ 172s] SKIPPED [63] passlib/tests/utils.py:2055: handler doesn't derive from HasManyIdents
[ 172s] SKIPPED [60] passlib/tests/utils.py:2172: truncate_size not set
[ 172s] SKIPPED [18] passlib/tests/utils.py:1093: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:1125: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:1166: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:1175: only default backend is being tested
[ 172s] SKIPPED [17] passlib/tests/utils.py:1230: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:1234: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:1269: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:1322: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:1375: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:1396: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:1422: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:1485: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:1521: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:1595: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:1625: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:1641: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:2004: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:2281: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:2319: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:2334: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:2345: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:2376: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:2614: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:2420: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:2667: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:2445: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:2480: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:2501: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:2522: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:2560: only default backend is being tested
[ 172s] SKIPPED [1] passlib/tests/test_handlers.py:208: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:2773: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:3079: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:2055: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:1788: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:1973: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:1706: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:1848: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:1732: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:1886: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:1932: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:1907: only default backend is being tested
[ 172s] SKIPPED [1] passlib/tests/test_handlers.py:213: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:2172: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:2140: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:2107: only default backend is being tested
[ 172s] SKIPPED [18] passlib/tests/utils.py:1541: only default backend is being tested
[ 172s] SKIPPED [44] passlib/tests/utils.py:1595: handler lacks rounds attributes
[ 172s] SKIPPED [44] passlib/tests/utils.py:1625: handler lacks rounds attributes
[ 172s] SKIPPED [44] passlib/tests/utils.py:1641: handler lacks rounds attributes
[ 172s] SKIPPED [44] passlib/tests/utils.py:1788: handler lacks rounds attributes
[ 172s] SKIPPED [44] passlib/tests/utils.py:1973: handler lacks rounds attributes
[ 172s] SKIPPED [44] passlib/tests/utils.py:1706: handler lacks rounds attributes
[ 172s] SKIPPED [44] passlib/tests/utils.py:1848: handler lacks rounds attributes
[ 172s] SKIPPED [44] passlib/tests/utils.py:1732: handler lacks rounds attributes
[ 172s] SKIPPED [44] passlib/tests/utils.py:1886: handler lacks rounds attributes
[ 172s] SKIPPED [44] passlib/tests/utils.py:1932: handler lacks rounds attributes
[ 172s] SKIPPED [44] passlib/tests/utils.py:1907: handler lacks rounds attributes
[ 172s] SKIPPED [8] passlib/tests/utils.py:2140: truncate_size is set
[ 172s] SKIPPED [17] passlib/tests/utils.py:2684: only default backend is being tested
[ 172s] SKIPPED [9] passlib/tests/utils.py:2614: parsehash() not implemented
[ 172s] SKIPPED [9] passlib/tests/utils.py:2667: parsehash() not implemented
[ 172s] SKIPPED [47] passlib/tests/utils.py:2480: no unidentified hashes provided
[ 172s] SKIPPED [2] passlib/tests/utils.py:3349: not applicable to wrappers
[ 172s] SKIPPED [1] passlib/tests/test_handlers.py:711: unneeded
[ 172s] SKIPPED [53] passlib/tests/utils.py:1269: handler only has one backend
[ 172s] SKIPPED [58] passlib/tests/utils.py:2345: none listed
[ 172s] SKIPPED [25] passlib/tests/utils.py:1322: handler doesn't have salt
[ 172s] SKIPPED [25] passlib/tests/utils.py:1375: handler doesn't have salt
[ 172s] SKIPPED [25] passlib/tests/utils.py:1396: handler doesn't have salt
[ 172s] SKIPPED [25] passlib/tests/utils.py:1422: handler doesn't have salt
[ 172s] SKIPPED [25] passlib/tests/utils.py:1485: handler doesn't have salt
[ 172s] SKIPPED [25] passlib/tests/utils.py:1521: handler doesn't have salt
[ 172s] SKIPPED [23] passlib/tests/utils.py:2445: hash has no settings
[ 172s] SKIPPED [25] passlib/tests/utils.py:1541: handler doesn't have salt
[ 172s] SKIPPED [1] passlib/tests/test_handlers.py:501: test case doesn't support 'realm' keyword
[ 172s] SKIPPED [2] passlib/tests/utils.py:2522: not applicable
[ 172s] SKIPPED [3] passlib/tests/utils.py:2684: not applicable
[ 172s] SKIPPED [1] passlib/tests/test_handlers_argon2.py:218: legacy 1.6 workflow not supported
[ 172s] SKIPPED [1] passlib/tests/test_handlers_argon2.py:218: only default backend is being tested
[ 172s] SKIPPED [1] passlib/tests/test_handlers_argon2.py:394: only default backend is being tested
[ 172s] SKIPPED [1] passlib/tests/test_handlers_argon2.py:231: only default backend is being tested
[ 172s] SKIPPED [1] passlib/tests/test_handlers_argon2.py:289: only default backend is being tested
[ 172s] SKIPPED [1] passlib/tests/test_handlers_argon2.py:222: only default backend is being tested
[ 172s] SKIPPED [1] passlib/tests/test_handlers_argon2.py:375: only default backend is being tested
[ 172s] SKIPPED [1] passlib/tests/test_handlers_argon2.py:384: only default backend is being tested
[ 172s] SKIPPED [1] passlib/tests/test_handlers_argon2.py:295: only default backend is being tested
[ 172s] SKIPPED [1] passlib/tests/test_handlers_argon2.py:333: only default backend is being tested
[ 172s] SKIPPED [1] passlib/tests/test_handlers_bcrypt.py:350: requires >= 'full' test mode
[ 172s] SKIPPED [4] passlib/tests/test_handlers_bcrypt.py:350: only default backend is being tested
[ 172s] SKIPPED [4] passlib/tests/test_handlers_bcrypt.py:408: only default backend is being tested
[ 172s] SKIPPED [1] passlib/tests/utils.py:2004: multiple idents not supported
[ 172s] SKIPPED [1] passlib/tests/utils.py:2055: multiple idents not supported
[ 172s] SKIPPED [4] passlib/tests/test_handlers_bcrypt.py:602: only default backend is being tested
[ 172s] SKIPPED [4] passlib/tests/test_handlers_bcrypt.py:641: only default backend is being tested
[ 172s] SKIPPED [4] passlib/tests/test_handlers_bcrypt.py:625: only default backend is being tested
[ 172s] SKIPPED [2] passlib/tests/utils.py:3310: only default backend is being tested
[ 172s] SKIPPED [2] passlib/tests/utils.py:3328: only default backend is being tested
[ 172s] SKIPPED [1] passlib/tests/utils.py:3349: no data for 'linux' platform (current host support = True)
[ 172s] SKIPPED [1] passlib/tests/utils.py:1322: handler doesn't provide salt info
[ 172s] SKIPPED [1] passlib/tests/utils.py:1396: handler doesn't provide salt info
[ 172s] SKIPPED [1] passlib/tests/utils.py:1422: handler doesn't provide salt info
[ 172s] SKIPPED [1] passlib/tests/utils.py:1485: handler doesn't provide salt info
[ 172s] SKIPPED [1] passlib/tests/utils.py:1541: handler doesn't provide salt info
[ 172s] SKIPPED [3] passlib/tests/test_handlers_django.py:82: Django <= 1.9 not installed
[ 172s] SKIPPED [3] passlib/tests/test_handlers_django.py:97: Django <= 1.9 not installed
[ 172s] SKIPPED [1] passlib/tests/test_handlers_django.py:82: Django <= 2.0 not installed
[ 172s] SKIPPED [1] passlib/tests/test_handlers_django.py:97: Django <= 2.0 not installed
[ 172s] SKIPPED [1] passlib/tests/test_handlers_django.py:397: legacy 1.6 workflow not supported
[ 172s] ==== 14 failed, 2130 passed, 2285 skipped, 28 warnings in 161.61s (0:02:41) ====
```
Full process how the package is tested and version of other packages is in the [full log](/uploads/2c3d2db5d98e0517245b30486620e551/_log.txt).https://foss.heptapod.net/python-libs/passlib/-/issues/130choose_rounds.py typo2022-11-17T14:50:45ZFilip Brzekchoose_rounds.py typo`choose_rounds.py` has a typo on line 160. Not sure how to send an MR, so I'm posting the patch file.
```
# HG changeset patch
# User Filip Brzek <filip.brzek@gmail.com>
# Date 1609064006 -3600
# Sun Dec 27 11:13:26 2020 +0100
# Br...`choose_rounds.py` has a typo on line 160. Not sure how to send an MR, so I'm posting the patch file.
```
# HG changeset patch
# User Filip Brzek <filip.brzek@gmail.com>
# Date 1609064006 -3600
# Sun Dec 27 11:13:26 2020 +0100
# Branch bugfix/choose_rounds_typo
# Node ID 0de7272f239da57f67bb310216eeb7fd86a801f1
# Parent 7aafcc60b4f5a3250c835f869a6a291ca3a3807b
prin -> print typo
diff -r 7aafcc60b4f5 -r 0de7272f239d choose_rounds.py
--- a/choose_rounds.py Thu Oct 08 15:01:32 2020 -0400
+++ b/choose_rounds.py Sun Dec 27 11:13:26 2020 +0100
@@ -157,7 +157,7 @@
print("target rounds...: %d" % upper)
else:
faster = (target - lower_elapsed)
- prin("target rounds...: %d (%dms -- %dms/%d%% faster than requested)" % \
+ print("target rounds...: %d (%dms -- %dms/%d%% faster than requested)" % \
(lower, lower_elapsed*1000, faster * 1000, round(100 * faster / target)))
slower = (upper_elapsed - target)
print("target rounds...: %d (%dms -- %dms/%d%% slower than requested)" % \
```https://foss.heptapod.net/python-libs/passlib/-/issues/134Minor highlight-breaking issue due to malformed docstring2022-11-17T14:05:51ZMingye WangMinor highlight-breaking issue due to malformed docstringI can't quite find a way to Fork & PR on here (could be my network?), so I have to shamelessly bug you people with an issue instead. Anyways, the line at https://foss.heptapod.net/python-libs/passlib/-/blob/0a09aa0e786fc33de74f847729e245...I can't quite find a way to Fork & PR on here (could be my network?), so I have to shamelessly bug you people with an issue instead. Anyways, the line at https://foss.heptapod.net/python-libs/passlib/-/blob/0a09aa0e786fc33de74f847729e245136346d194/passlib/utils/handlers.py#L2347 breaks GitLab's syntax highlighting. Adding two double-quotes to its start to form a proper docstring should fix it.
I mean, it's technically a GitLab bug, but it's not exactly right to leave functions like that...https://foss.heptapod.net/python-libs/passlib/-/issues/133CryptContext.verify requires unicode hash argument.2022-11-17T13:41:45ZMark SapiroCryptContext.verify requires unicode hash argument.Documentation for `CryptContext.verify(secret, hash, scheme=None, category=None, **kwds)` states that the `secret` and `hash` arguments can be either unicodes or bytes, but passing a valid `secret` and `hash` as a byte string produces:
`...Documentation for `CryptContext.verify(secret, hash, scheme=None, category=None, **kwds)` states that the `secret` and `hash` arguments can be either unicodes or bytes, but passing a valid `secret` and `hash` as a byte string produces:
```
... Traceback (most recent call last):
File "/var/MM/3/conf/mailman/src/mailman/utilities/passwords.py", line 62, in verify
ret = self._context.verify_and_update(password, hashed)
File "/var/MM/3/conf/mailman/.tox/py37-nocov/lib/python3.7/site-packages/passlib/context.py", line 2435, in verify_and_update
elif record.deprecated or record.needs_update(hash, secret=secret):
File "/var/MM/3/conf/mailman/.tox/py37-nocov/lib/python3.7/site-packages/passlib/utils/handlers.py", line 2672, in needs_update
hash = self._unwrap_hash(hash)
File "/var/MM/3/conf/mailman/.tox/py37-nocov/lib/python3.7/site-packages/passlib/utils/handlers.py", line 2640, in _unwrap_hash
if not hash.startswith(prefix):
TypeError: startswith first arg must be bytes or a tuple of bytes, not str
```https://foss.heptapod.net/python-libs/passlib/-/issues/139CryptContext should be a context manager2022-11-17T13:17:58ZMatthew PounsettCryptContext should be a context managerCryptContext seems like an obvious candidate to operate as a context manager, but it doesn't.
```python
>>> from passlib.context import CryptContext
>>> with CryptContext(schemes=['bcrypt']) as context:
... context.hash('foobar')
.....CryptContext seems like an obvious candidate to operate as a context manager, but it doesn't.
```python
>>> from passlib.context import CryptContext
>>> with CryptContext(schemes=['bcrypt']) as context:
... context.hash('foobar')
...
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
AttributeError: __enter__
>>>
```https://foss.heptapod.net/python-libs/passlib/-/issues/138Use SPDX license identifier2022-11-14T12:43:00ZMaximilianUse SPDX license identifierHi,
our project is using passlib as a dependency. So first of all thanks for the lib, nice features, love working with it...
Currently I'm working on our dependency management and I stumbled upon the license identifier for passlib on Py...Hi,
our project is using passlib as a dependency. So first of all thanks for the lib, nice features, love working with it...
Currently I'm working on our dependency management and I stumbled upon the license identifier for passlib on PyPi:
```
curl https://pypi.org/pypi/passlib/json | jq ".info.license"
"BSD"
```
Unfortunately this is not a valid SPDX identifier. There are a bunch of BSD-licenses see [here](https://spdx.github.io/spdx-spec/v2-draft/SPDX-license-list/) if you're not already bored enough.
When I follow the [link](https://opensource.org/licenses/bsd-license.php) in your `LICENSE` file the correct identifier would be `BSD-2-Clause`.
So could you be so kind and help my tool to use the right identifier? I think it would suffice to change it here:
https://foss.heptapod.net/python-libs/passlib/-/blob/branch/stable/setup.py#L43
Unfortunately I'm too dump to create a Merge request...
Thanks for having a look into this!https://foss.heptapod.net/python-libs/passlib/-/issues/131Max verification attemptswith wrong credentials2022-10-06T08:55:14ZDavidMax verification attemptswith wrong credentialsDoes passlib have a framework for handling false verification attempts (password, token, etc.)?
I read the docs but couldn't find any mention of this.
What I mean (at this topic I'm saying about wrong credentials exactly):
I see the foll...Does passlib have a framework for handling false verification attempts (password, token, etc.)?
I read the docs but couldn't find any mention of this.
What I mean (at this topic I'm saying about wrong credentials exactly):
I see the following working concept: passlib keeps the number of false attempts in memory for some time (say 5 minutes).
If the number of false attempts is exceeded during this time - passlib always returns false, even if the credentials are correct.
What is it for?
1. Prevent brute force attacks
2. Delegate authentication / authorization / verification logic to the library.
What currently solution I'm using for now: I'm storing false verification attempts inside a JWT tokenhttps://foss.heptapod.net/python-libs/passlib/-/issues/136passlib.hash.phpass docs error2021-09-10T23:14:38ZAbdelhafidh Belaliapasslib.hash.phpass docs errorJust a minor error in the docs of passlib.hash.phpass.
`rounds is a single character encoding a 6-bit integer representing the number of rounds used. This is logarithmic, the real number of rounds is 2**rounds. (in the example, rounds ...Just a minor error in the docs of passlib.hash.phpass.
`rounds is a single character encoding a 6-bit integer representing the number of rounds used. This is logarithmic, the real number of rounds is 2**rounds. (in the example, rounds is encoded as 8, or 2**13 iterations).
`
should be
`rounds is a single character encoding a 6-bit integer representing the number of rounds used. This is logarithmic, the real number of rounds is 2**rounds. (in the example, rounds is encoded as 8, or 2**10 iterations).`https://foss.heptapod.net/python-libs/passlib/-/issues/103Please add support for yescrypt2021-08-30T16:05:03ZBitbucket ImporterPlease add support for yescrypt*Created originally on Bitbucket by Anonymous*
[yescrypt](https://www.openwall.com/yescrypt/), an scrypt derivative, was one of the PHC contestants; despite not having been selected as the contest winner, it seems to be adopted somewhat...*Created originally on Bitbucket by Anonymous*
[yescrypt](https://www.openwall.com/yescrypt/), an scrypt derivative, was one of the PHC contestants; despite not having been selected as the contest winner, it seems to be adopted somewhat more widely than Argon2 (for instance, it's already showing up in Unix `crypt` implementations). Please add it to passlib.
A permissively licensed C implementation is [available from Openwall](https://cvsweb.openwall.com/cgi/cvsweb.cgi/projects/yescrypt/).Wishlist