Mercurial > hgrepos > Python > apps > py-cutils
comparison cutils/genpwd.py @ 240:32616df2732e
Renamed algorithms/repertoire selection: use a "bin-" prefix when just the output of os.urandom() is encoded
| author | Franz Glasner <fzglas.hg@dom66.de> |
|---|---|
| date | Sat, 08 Feb 2025 09:37:48 +0100 |
| parents | 1eae57292c7c |
| children | d4501acb0a7c |
comparison
equal
deleted
inserted
replaced
| 239:1eae57292c7c | 240:32616df2732e |
|---|---|
| 48 help="For some repertoires make OUTPUT-LENGTH the number of bytes" | 48 help="For some repertoires make OUTPUT-LENGTH the number of bytes" |
| 49 " that is to be read from random sources instead of output bytes") | 49 " that is to be read from random sources instead of output bytes") |
| 50 aparser.add_argument( | 50 aparser.add_argument( |
| 51 "--repertoire", "--type", "-t", | 51 "--repertoire", "--type", "-t", |
| 52 choices=("web", "web-safe", "web-safe2", | 52 choices=("web", "web-safe", "web-safe2", |
| 53 "base64", "urlsafe-base64", "urlsafe", "base32", "ascii85", ), | 53 "bin-base64", "bin-urlsafe-base64", "bin-base32", |
| 54 "bin-ascii85", ), | |
| 54 default="web-safe2", | 55 default="web-safe2", |
| 55 help="Select the character repertoire. Default: web-safe2") | 56 help="Select the character repertoire. Default: web-safe2") |
| 56 aparser.add_argument( | 57 aparser.add_argument( |
| 57 "req_length", metavar="OUTPUT-LENGTH", type=int, | 58 "req_length", metavar="OUTPUT-LENGTH", type=int, |
| 58 help="The required length of the generated output") | 59 help="The required length of the generated output") |
| 63 pwd = gen_from_repertoire(opts.req_length, WEB_CHARS) | 64 pwd = gen_from_repertoire(opts.req_length, WEB_CHARS) |
| 64 elif opts.repertoire == "web-safe": | 65 elif opts.repertoire == "web-safe": |
| 65 pwd = gen_from_repertoire(opts.req_length, WEB_SAFE_CHARS) | 66 pwd = gen_from_repertoire(opts.req_length, WEB_SAFE_CHARS) |
| 66 elif opts.repertoire == "web-safe2": | 67 elif opts.repertoire == "web-safe2": |
| 67 pwd = gen_from_repertoire(opts.req_length, WEB_SAFE2_CHARS) | 68 pwd = gen_from_repertoire(opts.req_length, WEB_SAFE2_CHARS) |
| 68 elif opts.repertoire == "base64": | 69 elif opts.repertoire == "bin-base64": |
| 69 encoder = base64.b64encode | 70 encoder = base64.b64encode |
| 70 pwd = gen_bin(opts.req_length, opts.use_bin_length, encoder, | 71 pwd = gen_bin(opts.req_length, opts.use_bin_length, encoder, |
| 71 rstrip_chars=b"=") | 72 rstrip_chars=b"=") |
| 72 elif opts.repertoire in ("urlsafe-base64", "urlsafe"): | 73 elif opts.repertoire == "bin-urlsafe-base64": |
| 73 encoder = base64.urlsafe_b64encode | 74 encoder = base64.urlsafe_b64encode |
| 74 pwd = gen_bin(opts.req_length, opts.use_bin_length, encoder, | 75 pwd = gen_bin(opts.req_length, opts.use_bin_length, encoder, |
| 75 rstrip_chars=b"=") | 76 rstrip_chars=b"=") |
| 76 elif opts.repertoire == "base32": | 77 elif opts.repertoire == "bin-base32": |
| 77 encoder = base64.b32encode | 78 encoder = base64.b32encode |
| 78 pwd = gen_bin(opts.req_length, opts.use_bin_length, encoder, | 79 pwd = gen_bin(opts.req_length, opts.use_bin_length, encoder, |
| 79 rstrip_chars=b"=") | 80 rstrip_chars=b"=") |
| 80 elif opts.repertoire == "ascii85": | 81 elif opts.repertoire == "bin-ascii85": |
| 81 encoder = base64.a85encode | 82 encoder = base64.a85encode |
| 82 pwd = gen_bin(opts.req_length, opts.use_bin_length, encoder) | 83 pwd = gen_bin(opts.req_length, opts.use_bin_length, encoder) |
| 83 else: | 84 else: |
| 84 raise NotImplementedError("type not yet implemented: %s" | 85 raise NotImplementedError("type not yet implemented: %s" |
| 85 % opts.repertoire) | 86 % opts.repertoire) |
| 93 pwd = pwd.decode("ascii") | 94 pwd = pwd.decode("ascii") |
| 94 print(pwd) | 95 print(pwd) |
| 95 | 96 |
| 96 | 97 |
| 97 def gen_from_repertoire(length, repertoire): | 98 def gen_from_repertoire(length, repertoire): |
| 99 """Select `length` characters randomly from given character repertoire | |
| 100 `repertoire`. | |
| 101 | |
| 102 """ | |
| 98 assert len(repertoire) <= 256 | 103 assert len(repertoire) <= 256 |
| 99 pwd = [] | 104 pwd = [] |
| 100 while len(pwd) < length: | 105 while len(pwd) < length: |
| 101 rndbytes = os.urandom(16) | 106 rndbytes = os.urandom(16) |
| 102 for c in rndbytes: | 107 for c in rndbytes: |
| 112 pwd = bytes(pwd) | 117 pwd = bytes(pwd) |
| 113 return pwd | 118 return pwd |
| 114 | 119 |
| 115 | 120 |
| 116 def gen_bin(length, use_bin_length, encoder, rstrip_chars=None): | 121 def gen_bin(length, use_bin_length, encoder, rstrip_chars=None): |
| 122 """Generate from :func:`os.urandom` and just encode with given `encoder`. | |
| 123 | |
| 124 """ | |
| 117 pwd = encoder(os.urandom(length)) | 125 pwd = encoder(os.urandom(length)) |
| 118 return pwd.rstrip(rstrip_chars) if use_bin_length else pwd[:length] | 126 return pwd.rstrip(rstrip_chars) if use_bin_length else pwd[:length] |
| 119 | 127 |
| 120 | 128 |
| 121 if __name__ == "__main__": | 129 if __name__ == "__main__": |
