Skip to content

Instantly share code, notes, and snippets.

@serverwentdown
Created July 12, 2019 01:21
Show Gist options
  • Save serverwentdown/ff721725a2db724132dd631bdb5a8994 to your computer and use it in GitHub Desktop.
Save serverwentdown/ff721725a2db724132dd631bdb5a8994 to your computer and use it in GitHub Desktop.
import random
import math
import string
import sys
import click
# correct horse battery staple
def load_dictionary(d="/usr/share/dict/words"):
f = open(d, "r")
words = f.readlines()
return list(
filter(
lambda w: w.isalpha(),
map(lambda w: w.strip().lower(), words)
)
)
def pick_words(words, n):
return random.choices(words, k=n)
def generate_password(words, sep="-", n=6, num=False):
words = pick_words(words, n)
if num:
for i in range(n):
digit = random.choice(string.digits)
words.insert(n-i-1, digit)
return sep.join(words)
@click.command()
@click.option("-c", "--count", default=4, help="Number of passwords to generate")
@click.option("-w", "--words", default=4, help="Number of words in a password")
@click.option("-s", "--sep", default="-", help="Seperator between words")
@click.option("--num/--no-num", default=False, help="Enable/disable adding numbers between words")
@click.option("--info/--no-info", default=True, help="Show/hide strength information")
@click.option("-d", "--dictionary", default="/usr/share/dict/words", help="Use a custom dictionary")
def program(count, words, sep, num, info, dictionary):
"""Generate a password from the system dictionary. xkcd.com/936"""
d = load_dictionary(dictionary)
if info:
combinations = len(d) ** words
if num:
combinations *= len(string.digits) ** words
print("With these options, there are {} possible passwords".format(combinations), file=sys.stderr)
conventional_set = len(string.ascii_letters) + len(string.digits) + len(string.punctuation)
conventional = math.ceil(math.log(combinations, conventional_set))
print("The strength is equivalent to a {} character \"strong\" password".format(conventional), file=sys.stderr)
print(file=sys.stderr)
for i in range(count):
p = generate_password(d, sep=sep, n=words, num=num)
print(p)
if __name__ == "__main__":
program()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment