Skip to content

Commit 1ed43f5

Browse files
committed
use optional third arg instead of env variable for max password length
1 parent 98a2b4d commit 1ed43f5

File tree

5 files changed

+22
-18
lines changed

5 files changed

+22
-18
lines changed

README.rst

Lines changed: 9 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -103,19 +103,19 @@ Output:
103103
}],
104104
}
105105

106-
To override the default maximum password length of 72 characters, set the
107-
``ZXCVBN_MAX_LENGTH`` environment variable:
106+
Another optional argument is ``max_length``, allowing override of the default max password length of 72.
107+
.. code:: python
108108
109-
.. code-block:: bash
109+
from zxcvbn import zxcvbn
110110
111-
export ZXCVBN_MAX_LENGTH=128
111+
results = zxcvbn('JohnSmith321', user_inputs=['John', 'Smith'], max_length=88)
112112
113113
.. warning::
114-
We strongly advise against setting ``ZXCVBN_MAX_LENGTH`` to a value greater than 72,
114+
115+
We strongly advise against setting ``max_length`` greater than 72,
115116
as it can lead to long processing times and may leave server-side applications open
116117
to denial-of-service scenarios.
117118

118-
119119
Custom Ranked Dictionaries
120120
--------------------------
121121

@@ -141,11 +141,13 @@ You an also use zxcvbn from the command line::
141141

142142
echo 'password' | zxcvbn --user-input <user-input> | jq
143143

144+
You can include a ``--max-length`` argument::
145+
echo '<long password>' | zxcvbn --max-length 142
146+
144147
You can also execute the zxcvbn module::
145148

146149
echo 'password' | python -m zxcvbn --user-input <user-input> | jq
147150

148-
149151
Contribute
150152
----------
151153

tests/l33t_exploit_test.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,6 @@ def test_l33t_exploit():
77

88
password = "4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/4@8({[</369&#!1/|0$5+7%2/"
99

10-
# Function should raise ValueError for input exceeding default MAX_LENGTH of 72 chars
11-
with pytest.raises(ValueError, match="Password length exceeds 72 characters"):
10+
# Function should raise ValueError for input exceeding default max_length of 72 chars
11+
with pytest.raises(ValueError, match="Password exceeds max length of 72 characters"):
1212
zxcvbn(password, user_inputs=[None])

tests/zxcvbn_test.py

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -24,9 +24,7 @@ def test_long_password():
2424
input_ = None
2525
password = "weopiopdsjmkldjvoisdjfioejiojweopiopdsjmkldjvoisdjfioejiojweopiopdsjmkldjvoisdjfioejiojweopiopdsjmkldjvoisdjfioejiojweopiopdsjmkldjvoisdjfioejiojweopiopdsjmkldjvoisdjfioejiojweopiopdsjmkldjvoisdjfioejiojweopiopdsjmkldjvoisdjfioejiojweopiopdsjmkldjvoisdjfioejiojweopiopdsjmkldjvoisdjfioejiojweopiopdsjmkldjvoisdjfioej"
2626

27-
# Function should raise ValueError for input exceeding default MAX_LENGTH of 72 chars
28-
with pytest.raises(ValueError, match="Password length exceeds 72 characters"):
29-
zxcvbn(password, user_inputs=[input_])
27+
zxcvbn(password, user_inputs=[input_], max_length=316)
3028

3129

3230
def test_dictionary_password():

zxcvbn/__init__.py

Lines changed: 3 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -3,13 +3,11 @@
33

44
from . import matching, scoring, time_estimates, feedback
55

6-
DEFAULT_MAX_LENGTH = 72
7-
MAX_LENGTH = int(os.environ.get('ZXCVBN_MAX_LENGTH', DEFAULT_MAX_LENGTH))
86

9-
def zxcvbn(password, user_inputs=None):
7+
def zxcvbn(password, user_inputs=None, max_length=72):
108
# Throw error if password exceeds max length
11-
if len(password) > MAX_LENGTH:
12-
raise ValueError(f"Password length exceeds {MAX_LENGTH} characters.")
9+
if len(password) > max_length:
10+
raise ValueError(f"Password exceeds max length of {max_length} characters.")
1311

1412
try:
1513
# Python 2 string types

zxcvbn/__main__.py

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,12 @@
1616
help='user data to be added to the dictionaries that are tested against '
1717
'(name, birthdate, etc)',
1818
)
19+
parser.add_argument(
20+
'--max-length',
21+
default=72,
22+
type=int,
23+
help='Override password max length (default: 72)'
24+
)
1925

2026
class JSONEncoder(json.JSONEncoder):
2127
def default(self, o):
@@ -36,7 +42,7 @@ def cli():
3642
else:
3743
password = getpass.getpass()
3844

39-
res = zxcvbn(password, user_inputs=args.user_input)
45+
res = zxcvbn(password, user_inputs=args.user_input, max_length=args.max_length)
4046
json.dump(res, sys.stdout, indent=2, cls=JSONEncoder)
4147
sys.stdout.write('\n')
4248

0 commit comments

Comments
 (0)