Passed
Push — master ( 227024...1d0698 )
by Oleksandr
02:44
created

tabpy.tabpy_server.app.util.parse_pwd_file()   C

Complexity

Conditions 9

Size

Total Lines 57
Code Lines 29

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
eloc 29
dl 0
loc 57
rs 6.6666
c 0
b 0
f 0
cc 9
nop 1

How to fix   Long Method   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
import csv
2
from datetime import datetime
3
import logging
4
from OpenSSL import crypto
5
import os
6
7
8
logger = logging.getLogger(__name__)
9
10
11
def validate_cert(cert_file_path):
12
    with open(cert_file_path, 'r') as f:
13
        cert_buf = f.read()
14
15
    cert = crypto.load_certificate(crypto.FILETYPE_PEM, cert_buf)
16
17
    date_format, encoding = '%Y%m%d%H%M%SZ', 'ascii'
18
    not_before = datetime.strptime(
19
        cert.get_notBefore().decode(encoding), date_format)
20
    not_after = datetime.strptime(
21
        cert.get_notAfter().decode(encoding), date_format)
22
    now = datetime.now()
23
24
    https_error = 'Error using HTTPS: '
25
    if now < not_before:
26
        msg = (https_error +
27
               f'The certificate provided is not valid until {not_before}.')
28
        logger.critical(msg)
29
        raise RuntimeError(msg)
30
    if now > not_after:
31
        msg = (https_error +
32
               f'The certificate provided expired on {not_after}.')
33
        logger.critical(msg)
34
        raise RuntimeError(msg)
35
36
37
def parse_pwd_file(pwd_file_name):
38
    '''
39
    Parses passwords file and returns set of credentials.
40
41
    Parameters
42
    ----------
43
    pwd_file_name : str
44
        Passwords file name.
45
46
    Returns
47
    -------
48
    succeeded : bool
49
        True if specified file was parsed successfully.
50
        False if there were any issues with parsing specified file.
51
52
    credentials : dict
53
        Credentials from the file. Empty if succeeded is False.
54
    '''
55
    logger.info(f'Parsing passwords file {pwd_file_name}...')
56
57
    if not os.path.isfile(pwd_file_name):
58
        logger.critical(f'Passwords file {pwd_file_name} not found')
59
        return False, {}
60
61
    credentials = {}
62
    with open(pwd_file_name) as pwd_file:
63
        pwd_file_reader = csv.reader(pwd_file, delimiter=' ')
64
        for row in pwd_file_reader:
65
            # skip empty lines
66
            if len(row) == 0:
67
                continue
68
69
            # skip commented lines
70
            if row[0][0] == '#':
71
                continue
72
73
            if len(row) != 2:
74
                logger.error(
75
                    f'Incorrect entry "{row}" in password file')
76
                return False, {}
77
78
            login = row[0].lower()
79
            if login in credentials:
80
                logger.error(
81
                    f'Multiple entries for username {login} '
82
                    'in password file')
83
                return False, {}
84
85
            if(len(row[1]) > 0):
86
                credentials[login] = row[1]
87
                logger.debug(f'Found username {login}')
88
            else:
89
                logger.warning(f'Found username {row[0]} but no password')
90
                return False, {}
91
92
    logger.info("Authentication is enabled")
93
    return True, credentials
94