~barry/mailman/events-and-web

« back to all changes in this revision

Viewing changes to src/mailman/utilities/passwords.py

  • Committer: Barry Warsaw
  • Date: 2012-06-28 03:03:04 UTC
  • mto: This revision was merged to the branch mainline in revision 7156.
  • Revision ID: barry@list.org-20120628030304-cjlh7q9tgwasxno2
Replace flufl.password with passlib, albeit with a wrapper.

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
# Copyright (C) 2012 by the Free Software Foundation, Inc.
 
2
#
 
3
# This file is part of GNU Mailman.
 
4
#
 
5
# GNU Mailman is free software: you can redistribute it and/or modify it under
 
6
# the terms of the GNU General Public License as published by the Free
 
7
# Software Foundation, either version 3 of the License, or (at your option)
 
8
# any later version.
 
9
#
 
10
# GNU Mailman is distributed in the hope that it will be useful, but WITHOUT
 
11
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
 
12
# FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
 
13
# more details.
 
14
#
 
15
# You should have received a copy of the GNU General Public License along with
 
16
# GNU Mailman.  If not, see <http://www.gnu.org/licenses/>.
 
17
 
 
18
"""A wrapper around passlib."""
 
19
 
 
20
from __future__ import absolute_import, print_function, unicode_literals
 
21
 
 
22
__metaclass__ = type
 
23
__all__ = [
 
24
    'encrypt',
 
25
    'verify',
 
26
    ]
 
27
 
 
28
 
 
29
import re
 
30
 
 
31
from passlib.registry import get_crypt_handler
 
32
 
 
33
from mailman.config import config
 
34
from mailman.testing import layers
 
35
from mailman.utilities.modules import find_name
 
36
 
 
37
SCHEME_RE = r'{(?P<scheme>[^}]+?)}(?P<rest>.*)'.encode()
 
38
 
 
39
 
 
40
 
 
41
def encrypt(secret):
 
42
    hasher = find_name(config.passwords.password_scheme)
 
43
    # For reproducibility, don't use any salt in the test suite.
 
44
    kws = {}
 
45
    if layers.is_testing and 'salt' in hasher.setting_kwds:
 
46
        kws['salt'] = b''
 
47
    hashed = hasher.encrypt(secret, **kws)
 
48
    return b'{{{0}}}{1}'.format(hasher.name, hashed)
 
49
 
 
50
 
 
51
def verify(hashed, password):
 
52
    mo = re.match(SCHEME_RE, hashed, re.IGNORECASE)
 
53
    if not mo:
 
54
        return False
 
55
    scheme, secret = mo.groups(('scheme', 'rest'))
 
56
    hasher = get_crypt_handler(scheme)
 
57
    return hasher.verify(password, secret)