Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit 98543be

Browse files
committed
added solution for 20
1 parent 9e8d9ac commit 98543be

File tree

1 file changed

+131
-0
lines changed

1 file changed

+131
-0
lines changed

20_password/password.py

Lines changed: 131 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,131 @@
1+
#!/usr/bin/env python3
2+
"""
3+
Author : Martin Schuh <[email protected]>
4+
Date : 2022-11-22
5+
Purpose: Password maker
6+
"""
7+
8+
import argparse
9+
import sys
10+
from typing import Final
11+
import string
12+
import random
13+
14+
15+
LEET_CODE: Final = {
16+
'a': '@',
17+
'A': '4',
18+
'O': '0',
19+
't': '+',
20+
'E': '3',
21+
'I': '1',
22+
'S': '5'
23+
}
24+
25+
26+
# --------------------------------------------------
27+
def get_args():
28+
"""Get command-line arguments"""
29+
30+
parser = argparse.ArgumentParser(
31+
description='Password maker',
32+
formatter_class=argparse.ArgumentDefaultsHelpFormatter)
33+
34+
parser.add_argument('file',
35+
metavar='FILE',
36+
type=argparse.FileType('rt'),
37+
nargs='+',
38+
default=[sys.stdin],
39+
help='Input file(s)')
40+
41+
parser.add_argument('-n',
42+
'--num',
43+
help='Number of passwords to generate',
44+
metavar='num_passwords',
45+
type=int,
46+
default=3)
47+
48+
parser.add_argument('-w',
49+
'--num_words',
50+
help='Number of words to use for password',
51+
metavar='num_words',
52+
type=int,
53+
default=4)
54+
55+
parser.add_argument('-m',
56+
'--min_word_len',
57+
help='Minimum word length',
58+
metavar='minimum',
59+
type=int,
60+
default=3)
61+
62+
parser.add_argument('-x',
63+
'--max_word_len',
64+
help='Maximum word length',
65+
metavar='maximum',
66+
type=int,
67+
default=6)
68+
69+
parser.add_argument('-s',
70+
'--seed',
71+
help='Random seed',
72+
metavar='seed',
73+
type=int,
74+
default=None)
75+
76+
parser.add_argument('-l',
77+
'--l33t',
78+
help='Obfuscate letters',
79+
action='store_true')
80+
81+
return parser.parse_args()
82+
83+
84+
# --------------------------------------------------
85+
def main():
86+
"""Make a jazz noise here"""
87+
88+
args = get_args()
89+
random.seed(args.seed)
90+
91+
words = set()
92+
93+
def word_len(word):
94+
return args.min_word_len <= len(word) <= args.max_word_len
95+
96+
for file_handle in args.file:
97+
for line in file_handle:
98+
for word in filter(word_len, map(clean, line.lower().split())):
99+
words.add(word.title())
100+
101+
words = sorted(words)
102+
passwords = [''.join(random.sample(words, args.num_words))
103+
for _ in range(args.num)]
104+
105+
if args.l33t:
106+
passwords = list(map(l33t, passwords))
107+
108+
print('\n'.join(passwords))
109+
110+
111+
# --------------------------------------------------
112+
def clean(text: str):
113+
"""Removes punctuation chars from string"""
114+
return ''.join(filter(lambda c: c not in string.punctuation, text))
115+
116+
117+
def ransom(text: str):
118+
"""Swaps char sensitiveness randomly"""
119+
return ''.join([c.upper() if random.choice([False, True]) else c.lower()
120+
for c in text])
121+
122+
123+
def l33t(text: str):
124+
"""Encodes char in l33t style"""
125+
return ''.join([LEET_CODE.get(c, c) for c in ransom(text)])\
126+
+ random.choice(string.punctuation)
127+
128+
129+
# --------------------------------------------------
130+
if __name__ == '__main__':
131+
main()

0 commit comments

Comments
 (0)