kpass-gen 0.2.1__tar.gz → 0.2.5__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- kpass_gen-0.2.5/PKG-INFO +191 -0
- kpass_gen-0.2.5/README.md +142 -0
- {kpass_gen-0.2.1 → kpass_gen-0.2.5}/kpass/__init__.py +6 -6
- kpass_gen-0.2.5/kpass/main.py +239 -0
- kpass_gen-0.2.5/kpass_gen.egg-info/PKG-INFO +191 -0
- kpass_gen-0.2.5/pyproject.toml +57 -0
- kpass_gen-0.2.1/PKG-INFO +0 -175
- kpass_gen-0.2.1/README.md +0 -138
- kpass_gen-0.2.1/kpass/main.py +0 -221
- kpass_gen-0.2.1/kpass_gen.egg-info/PKG-INFO +0 -175
- kpass_gen-0.2.1/pyproject.toml +0 -30
- {kpass_gen-0.2.1 → kpass_gen-0.2.5}/LICENSE.txt +0 -0
- {kpass_gen-0.2.1 → kpass_gen-0.2.5}/kpass_gen.egg-info/SOURCES.txt +0 -0
- {kpass_gen-0.2.1 → kpass_gen-0.2.5}/kpass_gen.egg-info/dependency_links.txt +0 -0
- {kpass_gen-0.2.1 → kpass_gen-0.2.5}/kpass_gen.egg-info/requires.txt +0 -0
- {kpass_gen-0.2.1 → kpass_gen-0.2.5}/kpass_gen.egg-info/top_level.txt +0 -0
- {kpass_gen-0.2.1 → kpass_gen-0.2.5}/setup.cfg +0 -0
kpass_gen-0.2.5/PKG-INFO
ADDED
@@ -0,0 +1,191 @@
|
|
1
|
+
Metadata-Version: 2.4
|
2
|
+
Name: kpass-gen
|
3
|
+
Version: 0.2.5
|
4
|
+
Summary: kpass is a Python toolkit for generating, ciphering and evaluating passwords with JSON, CSV and YAML export.
|
5
|
+
Author-email: "Lucas Paulino Da Silva (~K')" <lucas.workps@gmail.com>
|
6
|
+
License: MIT License
|
7
|
+
|
8
|
+
Copyright (c) [year] [fullname]
|
9
|
+
|
10
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
11
|
+
of this software and associated documentation files (the "Software"), to deal
|
12
|
+
in the Software without restriction, including without limitation the rights
|
13
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
14
|
+
copies of the Software, and to permit persons to whom the Software is
|
15
|
+
furnished to do so, subject to the following conditions:
|
16
|
+
|
17
|
+
The above copyright notice and this permission notice shall be included in all
|
18
|
+
copies or substantial portions of the Software.
|
19
|
+
|
20
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
21
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
22
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
23
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
24
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
25
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
26
|
+
SOFTWARE.
|
27
|
+
Project-URL: homepage, https://github.com/lucaspy-stack/kpass
|
28
|
+
Project-URL: repository, https://github.com/lucaspy-stack/kpass
|
29
|
+
Keywords: password,generator,leet,name-based,cybersecurity,pentest,automation,security,rich,csv,yaml,json,python
|
30
|
+
Classifier: Development Status :: 4 - Beta
|
31
|
+
Classifier: Intended Audience :: Developers
|
32
|
+
Classifier: Topic :: Security :: Cryptography
|
33
|
+
Classifier: Topic :: Software Development :: Libraries :: Python Modules
|
34
|
+
Classifier: License :: OSI Approved :: MIT License
|
35
|
+
Classifier: Operating System :: OS Independent
|
36
|
+
Classifier: Programming Language :: Python :: 3
|
37
|
+
Classifier: Programming Language :: Python :: 3.6
|
38
|
+
Classifier: Programming Language :: Python :: 3.7
|
39
|
+
Classifier: Programming Language :: Python :: 3.8
|
40
|
+
Classifier: Programming Language :: Python :: 3.9
|
41
|
+
Classifier: Programming Language :: Python :: 3.10
|
42
|
+
Classifier: Programming Language :: Python :: 3.11
|
43
|
+
Classifier: Programming Language :: Python :: 3.12
|
44
|
+
Requires-Python: >=3.6
|
45
|
+
Description-Content-Type: text/markdown
|
46
|
+
License-File: LICENSE.txt
|
47
|
+
Requires-Dist: rich
|
48
|
+
Dynamic: license-file
|
49
|
+
|
50
|
+
# 🔐 kpass — Smart Password Generator & Evaluator
|
51
|
+
|
52
|
+
<p align="center">
|
53
|
+
<img src="assets/kpass_icon.png" alt="kpass logo" width="100%"/>
|
54
|
+
</p>
|
55
|
+
|
56
|
+
**kpass** is a Python toolkit for **generating**, **ciphering** and **evaluating** passwords—designed for **educational**, **testing** and **automation** scenarios.
|
57
|
+
|
58
|
+
---
|
59
|
+
|
60
|
+
## ✨ Features
|
61
|
+
|
62
|
+
* **Generate** hundreds or thousands of password combinations from:
|
63
|
+
|
64
|
+
* Full name
|
65
|
+
* Age
|
66
|
+
* Birth date
|
67
|
+
* **Leet‑speak** substitutions like `A → 4`, `E → 3`, `S → $`
|
68
|
+
* **Strength evaluation** based on:
|
69
|
+
|
70
|
+
* Length
|
71
|
+
* Digits
|
72
|
+
* Special characters
|
73
|
+
* Mixed case
|
74
|
+
* Numeric sequence patterns
|
75
|
+
* **Export** automatically to `.json`, `.csv` or `.yaml` with a progress bar powered by **rich**
|
76
|
+
|
77
|
+
---
|
78
|
+
|
79
|
+
## ⚠️ Security Disclaimer
|
80
|
+
|
81
|
+
This project **does not** produce secure passwords for production systems.
|
82
|
+
It uses **predictable** inputs (names, dates) and should **not** be used for real authentication.
|
83
|
+
|
84
|
+
---
|
85
|
+
|
86
|
+
## 🎯 Use Cases
|
87
|
+
|
88
|
+
* 🧠 **Cybersecurity Awareness**
|
89
|
+
Learn why personal info makes weak passwords.
|
90
|
+
|
91
|
+
* 🧰 **Pentesting & Wordlist Creation**
|
92
|
+
Build custom dictionaries for ethical hacking.
|
93
|
+
|
94
|
+
* 🧪 **Automation & Testing**
|
95
|
+
Generate dummy passwords for scripts, bots or sandbox environments.
|
96
|
+
|
97
|
+
---
|
98
|
+
|
99
|
+
## 📦 Installation
|
100
|
+
|
101
|
+
```bash
|
102
|
+
pip install kpass-gen
|
103
|
+
```
|
104
|
+
|
105
|
+
> Requires Python 3.6+
|
106
|
+
|
107
|
+
---
|
108
|
+
|
109
|
+
## 🚀 Quick Start
|
110
|
+
|
111
|
+
### 1. Generate Passwords
|
112
|
+
|
113
|
+
```python
|
114
|
+
from kpass import generator
|
115
|
+
|
116
|
+
# Example: Johnny Silverhand (born 08/07/2000, age 50 in 2077)
|
117
|
+
generator(
|
118
|
+
name="Johnny Silverhand",
|
119
|
+
age="50",
|
120
|
+
birth_date="08/07/2000",
|
121
|
+
file_type="json", # optional: json, csv, yaml or yml
|
122
|
+
file_name="jsilverhand" # optional: filename without extension
|
123
|
+
)
|
124
|
+
```
|
125
|
+
|
126
|
+
### 2. Apply Leet Cipher
|
127
|
+
|
128
|
+
```python
|
129
|
+
from kpass import apply_ciphers
|
130
|
+
|
131
|
+
# Example: Panam Palmer
|
132
|
+
leet = apply_ciphers("Panam Palmer")
|
133
|
+
print(leet) # → "|D4|\\|4/\\/\\ |D41/\\/\\312"
|
134
|
+
```
|
135
|
+
|
136
|
+
### 3. Save Custom Password Lists
|
137
|
+
|
138
|
+
```python
|
139
|
+
from kpass import save_to_file
|
140
|
+
|
141
|
+
# Example passwords inspired by Cyberpunk characters
|
142
|
+
passwords = ["Chipp4020!", "AltAccount2077$", "RoughTrade37#"]
|
143
|
+
scores = [3, 5, 4]
|
144
|
+
verdicts = ["#mean", "#strong", "#good"]
|
145
|
+
|
146
|
+
save_to_file(
|
147
|
+
passwords,
|
148
|
+
scores,
|
149
|
+
verdicts,
|
150
|
+
file_name="cyberpunk_list",
|
151
|
+
file_type="csv" # outputs cyberpunk_list.csv
|
152
|
+
)
|
153
|
+
```
|
154
|
+
|
155
|
+
### 4. Check Password Strength
|
156
|
+
|
157
|
+
```python
|
158
|
+
from kpass import verify
|
159
|
+
|
160
|
+
# returns "#very_strong"
|
161
|
+
print(verify("R0gueDr1ft!99"))
|
162
|
+
|
163
|
+
# returns 6
|
164
|
+
print(verify("R0gueDr1ft!99", want_verdict=False))
|
165
|
+
```
|
166
|
+
|
167
|
+
---
|
168
|
+
|
169
|
+
## 🔧 API Reference
|
170
|
+
|
171
|
+
| Function | Description |
|
172
|
+
| ----------------------------------------------------------------- | --------------------------------------------------------------------------- |
|
173
|
+
| `generator(name, age, birth_date, file_type, file_name)` | Generates permutations, evaluates strength, and saves to a file |
|
174
|
+
| `apply_ciphers(text)` | Applies leet‑speak substitutions |
|
175
|
+
| `save_to_file(passwords, scores, verdicts, file_name, file_type)` | Exports password list + scores + verdicts with a progress bar |
|
176
|
+
| `verify(password, want_verdict=True)` | Evaluates strength; returns an `int` score or `str` verdict (`#good`, etc.) |
|
177
|
+
| `check_sequences(password)` | Detects ascending/descending numeric sequences |
|
178
|
+
| `veredict(score)` | Maps numeric score to verdict string (`#weak`, `#strong`, etc.) |
|
179
|
+
|
180
|
+
---
|
181
|
+
|
182
|
+
## ✅ Requirements
|
183
|
+
|
184
|
+
* Python 3.6 or higher
|
185
|
+
* [rich](https://pypi.org/project/rich/) for progress bars
|
186
|
+
|
187
|
+
---
|
188
|
+
|
189
|
+
## 📄 License
|
190
|
+
|
191
|
+
MIT License — free to use, modify and share.
|
@@ -0,0 +1,142 @@
|
|
1
|
+
# 🔐 kpass — Smart Password Generator & Evaluator
|
2
|
+
|
3
|
+
<p align="center">
|
4
|
+
<img src="assets/kpass_icon.png" alt="kpass logo" width="100%"/>
|
5
|
+
</p>
|
6
|
+
|
7
|
+
**kpass** is a Python toolkit for **generating**, **ciphering** and **evaluating** passwords—designed for **educational**, **testing** and **automation** scenarios.
|
8
|
+
|
9
|
+
---
|
10
|
+
|
11
|
+
## ✨ Features
|
12
|
+
|
13
|
+
* **Generate** hundreds or thousands of password combinations from:
|
14
|
+
|
15
|
+
* Full name
|
16
|
+
* Age
|
17
|
+
* Birth date
|
18
|
+
* **Leet‑speak** substitutions like `A → 4`, `E → 3`, `S → $`
|
19
|
+
* **Strength evaluation** based on:
|
20
|
+
|
21
|
+
* Length
|
22
|
+
* Digits
|
23
|
+
* Special characters
|
24
|
+
* Mixed case
|
25
|
+
* Numeric sequence patterns
|
26
|
+
* **Export** automatically to `.json`, `.csv` or `.yaml` with a progress bar powered by **rich**
|
27
|
+
|
28
|
+
---
|
29
|
+
|
30
|
+
## ⚠️ Security Disclaimer
|
31
|
+
|
32
|
+
This project **does not** produce secure passwords for production systems.
|
33
|
+
It uses **predictable** inputs (names, dates) and should **not** be used for real authentication.
|
34
|
+
|
35
|
+
---
|
36
|
+
|
37
|
+
## 🎯 Use Cases
|
38
|
+
|
39
|
+
* 🧠 **Cybersecurity Awareness**
|
40
|
+
Learn why personal info makes weak passwords.
|
41
|
+
|
42
|
+
* 🧰 **Pentesting & Wordlist Creation**
|
43
|
+
Build custom dictionaries for ethical hacking.
|
44
|
+
|
45
|
+
* 🧪 **Automation & Testing**
|
46
|
+
Generate dummy passwords for scripts, bots or sandbox environments.
|
47
|
+
|
48
|
+
---
|
49
|
+
|
50
|
+
## 📦 Installation
|
51
|
+
|
52
|
+
```bash
|
53
|
+
pip install kpass-gen
|
54
|
+
```
|
55
|
+
|
56
|
+
> Requires Python 3.6+
|
57
|
+
|
58
|
+
---
|
59
|
+
|
60
|
+
## 🚀 Quick Start
|
61
|
+
|
62
|
+
### 1. Generate Passwords
|
63
|
+
|
64
|
+
```python
|
65
|
+
from kpass import generator
|
66
|
+
|
67
|
+
# Example: Johnny Silverhand (born 08/07/2000, age 50 in 2077)
|
68
|
+
generator(
|
69
|
+
name="Johnny Silverhand",
|
70
|
+
age="50",
|
71
|
+
birth_date="08/07/2000",
|
72
|
+
file_type="json", # optional: json, csv, yaml or yml
|
73
|
+
file_name="jsilverhand" # optional: filename without extension
|
74
|
+
)
|
75
|
+
```
|
76
|
+
|
77
|
+
### 2. Apply Leet Cipher
|
78
|
+
|
79
|
+
```python
|
80
|
+
from kpass import apply_ciphers
|
81
|
+
|
82
|
+
# Example: Panam Palmer
|
83
|
+
leet = apply_ciphers("Panam Palmer")
|
84
|
+
print(leet) # → "|D4|\\|4/\\/\\ |D41/\\/\\312"
|
85
|
+
```
|
86
|
+
|
87
|
+
### 3. Save Custom Password Lists
|
88
|
+
|
89
|
+
```python
|
90
|
+
from kpass import save_to_file
|
91
|
+
|
92
|
+
# Example passwords inspired by Cyberpunk characters
|
93
|
+
passwords = ["Chipp4020!", "AltAccount2077$", "RoughTrade37#"]
|
94
|
+
scores = [3, 5, 4]
|
95
|
+
verdicts = ["#mean", "#strong", "#good"]
|
96
|
+
|
97
|
+
save_to_file(
|
98
|
+
passwords,
|
99
|
+
scores,
|
100
|
+
verdicts,
|
101
|
+
file_name="cyberpunk_list",
|
102
|
+
file_type="csv" # outputs cyberpunk_list.csv
|
103
|
+
)
|
104
|
+
```
|
105
|
+
|
106
|
+
### 4. Check Password Strength
|
107
|
+
|
108
|
+
```python
|
109
|
+
from kpass import verify
|
110
|
+
|
111
|
+
# returns "#very_strong"
|
112
|
+
print(verify("R0gueDr1ft!99"))
|
113
|
+
|
114
|
+
# returns 6
|
115
|
+
print(verify("R0gueDr1ft!99", want_verdict=False))
|
116
|
+
```
|
117
|
+
|
118
|
+
---
|
119
|
+
|
120
|
+
## 🔧 API Reference
|
121
|
+
|
122
|
+
| Function | Description |
|
123
|
+
| ----------------------------------------------------------------- | --------------------------------------------------------------------------- |
|
124
|
+
| `generator(name, age, birth_date, file_type, file_name)` | Generates permutations, evaluates strength, and saves to a file |
|
125
|
+
| `apply_ciphers(text)` | Applies leet‑speak substitutions |
|
126
|
+
| `save_to_file(passwords, scores, verdicts, file_name, file_type)` | Exports password list + scores + verdicts with a progress bar |
|
127
|
+
| `verify(password, want_verdict=True)` | Evaluates strength; returns an `int` score or `str` verdict (`#good`, etc.) |
|
128
|
+
| `check_sequences(password)` | Detects ascending/descending numeric sequences |
|
129
|
+
| `veredict(score)` | Maps numeric score to verdict string (`#weak`, `#strong`, etc.) |
|
130
|
+
|
131
|
+
---
|
132
|
+
|
133
|
+
## ✅ Requirements
|
134
|
+
|
135
|
+
* Python 3.6 or higher
|
136
|
+
* [rich](https://pypi.org/project/rich/) for progress bars
|
137
|
+
|
138
|
+
---
|
139
|
+
|
140
|
+
## 📄 License
|
141
|
+
|
142
|
+
MIT License — free to use, modify and share.
|
@@ -1,19 +1,19 @@
|
|
1
1
|
from .main import (
|
2
2
|
generator,
|
3
|
-
|
4
|
-
|
3
|
+
save_to_file,
|
4
|
+
apply_ciphers,
|
5
5
|
check_sequences,
|
6
6
|
veredict,
|
7
7
|
verify,
|
8
8
|
)
|
9
9
|
|
10
|
-
__version__ = "0.2.
|
10
|
+
__version__ = "0.2.5"
|
11
11
|
|
12
12
|
__all__ = [
|
13
13
|
"generator",
|
14
|
-
"
|
15
|
-
"
|
14
|
+
"save_to_file",
|
15
|
+
"apply_ciphers",
|
16
16
|
"check_sequences",
|
17
17
|
"veredict",
|
18
18
|
"verify",
|
19
|
-
]
|
19
|
+
]
|
@@ -0,0 +1,239 @@
|
|
1
|
+
import itertools
|
2
|
+
from rich.progress import Progress, BarColumn, TextColumn, TimeElapsedColumn
|
3
|
+
import re
|
4
|
+
import string
|
5
|
+
import json
|
6
|
+
from math import perm
|
7
|
+
from datetime import datetime
|
8
|
+
from pathlib import Path
|
9
|
+
|
10
|
+
# -----------------------------------------------------------------------------
|
11
|
+
# Ciphers dictionary to replace letters with leetspeak equivalents
|
12
|
+
# Each key is a character and the corresponding value is its cipher substitution
|
13
|
+
# -----------------------------------------------------------------------------
|
14
|
+
|
15
|
+
ciphers = {
|
16
|
+
"A": "4", "a": "4", "Á": "4", "á": "4", "@": "4",
|
17
|
+
"B": "8", "b": "8",
|
18
|
+
"C": "(", "c": "(",
|
19
|
+
"D": "[)", "d": "[)",
|
20
|
+
"E": "3", "e": "3", "É": "3", "é": "3", "&": "3",
|
21
|
+
"F": "#", "f": "#",
|
22
|
+
"G": "6", "g": "6",
|
23
|
+
"H": "#", "h": "#",
|
24
|
+
"I": "1", "i": "1", "Í": "1", "í": "1", "!": "1",
|
25
|
+
"J": "_|", "j": "_|",
|
26
|
+
"K": "|<", "k": "|<",
|
27
|
+
"L": "1", "l": "1",
|
28
|
+
"M": "/\\/\\", "m": "/\\/\\",
|
29
|
+
"N": "|\\|", "n": "|\\|",
|
30
|
+
"O": "0", "o": "0", "Ó": "0", "ó": "0",
|
31
|
+
"P": "|D", "p": "|D",
|
32
|
+
"Q": "0_", "q": "0_",
|
33
|
+
"R": "12", "r": "12",
|
34
|
+
"S": "$", "s": "$", "Š": "$", "š": "$",
|
35
|
+
"T": "7", "t": "7",
|
36
|
+
"U": "(_)", "u": "(_)",
|
37
|
+
"V": "\\/", "v": "\\/",
|
38
|
+
"W": "\\/\\/", "w": "\\/\\/",
|
39
|
+
"X": "%", "x": "%",
|
40
|
+
"Y": "`/", "y": "`/",
|
41
|
+
"Z": "2", "z": "2"
|
42
|
+
}
|
43
|
+
|
44
|
+
# -----------------------------------------------------------------------------
|
45
|
+
# Function: apply_ciphers
|
46
|
+
# Description:
|
47
|
+
# Transforms input text by replacing each character according to the ciphers dict
|
48
|
+
# Parameters:
|
49
|
+
# text (str): The original text to be ciphered
|
50
|
+
# Returns:
|
51
|
+
# str: The transformed text with cipher substitutions
|
52
|
+
# -----------------------------------------------------------------------------
|
53
|
+
|
54
|
+
def apply_ciphers(text: str) -> str:
|
55
|
+
return ''.join(ciphers.get(char, char) for char in text)
|
56
|
+
|
57
|
+
# -----------------------------------------------------------------------------
|
58
|
+
# Utility: write with progress bar
|
59
|
+
# -----------------------------------------------------------------------------
|
60
|
+
|
61
|
+
def _write_with_progress(write_fn, items):
|
62
|
+
with Progress(
|
63
|
+
TextColumn("[progress.description]{task.description}"),
|
64
|
+
BarColumn(),
|
65
|
+
TimeElapsedColumn(),
|
66
|
+
) as progress:
|
67
|
+
task = progress.add_task("[cyan]Saving passwords...", total=len(items))
|
68
|
+
for item in items:
|
69
|
+
write_fn(item)
|
70
|
+
progress.update(task, advance=1)
|
71
|
+
|
72
|
+
# -----------------------------------------------------------------------------
|
73
|
+
# Function: save_to_file
|
74
|
+
# Description:
|
75
|
+
# Writes a list of passwords, scores, and verdicts to a file with progress
|
76
|
+
# Parameters:
|
77
|
+
# passwords (list[str]): List of password strings
|
78
|
+
# scores (list[int]): Corresponding strength scores
|
79
|
+
# verdicts (list[str]): Corresponding verdict strings
|
80
|
+
# file_name (str): Output filename without extension
|
81
|
+
# file_type (str): Extension (json, csv, yaml, yml)
|
82
|
+
# Returns:
|
83
|
+
# None
|
84
|
+
# -----------------------------------------------------------------------------
|
85
|
+
|
86
|
+
def save_to_file(
|
87
|
+
passwords: list[str],
|
88
|
+
scores: list[int],
|
89
|
+
verdicts: list[str],
|
90
|
+
file_name: str = "pass_generated",
|
91
|
+
file_type: str = "json"
|
92
|
+
) -> None:
|
93
|
+
extension = file_type.lstrip('.')
|
94
|
+
path = Path(f"{file_name}.{extension}")
|
95
|
+
path.write_text("", encoding="utf-8-sig") # limpa conteúdo existente
|
96
|
+
|
97
|
+
def writer_json(item):
|
98
|
+
pwd, score, verdict = item
|
99
|
+
return json.dumps({"password": pwd, "score": score, "veredict": verdict}, indent=4, ensure_ascii=False) + "\n"
|
100
|
+
|
101
|
+
def writer_csv(item):
|
102
|
+
pwd, score, verdict = item
|
103
|
+
return (
|
104
|
+
f'"password","{pwd}",\n'
|
105
|
+
f'"score","{score}",\n'
|
106
|
+
f'"veredict","{verdict}"\n\\n'
|
107
|
+
)
|
108
|
+
|
109
|
+
def writer_yaml(item):
|
110
|
+
pwd, score, verdict = item
|
111
|
+
return (
|
112
|
+
f'"password": "{pwd}"\n'
|
113
|
+
f'"score": "{score}"\n'
|
114
|
+
f'"veredict": "{verdict}"\n\\n'
|
115
|
+
)
|
116
|
+
|
117
|
+
if extension == "json":
|
118
|
+
writer = writer_json
|
119
|
+
elif extension == "csv":
|
120
|
+
writer = writer_csv
|
121
|
+
elif extension in ("yaml", "yml"):
|
122
|
+
writer = writer_yaml
|
123
|
+
else:
|
124
|
+
raise ValueError(f"Unsupported file type: {file_type}")
|
125
|
+
|
126
|
+
items = list(zip(passwords, scores, verdicts))
|
127
|
+
with Progress(
|
128
|
+
TextColumn("[progress.description]{task.description}"),
|
129
|
+
BarColumn(),
|
130
|
+
TimeElapsedColumn(),
|
131
|
+
) as progress:
|
132
|
+
task = progress.add_task("[cyan]Saving passwords...", total=len(items))
|
133
|
+
with path.open("a", encoding="utf-8-sig") as file:
|
134
|
+
for item in items:
|
135
|
+
file.write(writer(item))
|
136
|
+
progress.update(task, advance=1)
|
137
|
+
|
138
|
+
# -----------------------------------------------------------------------------
|
139
|
+
# Function: base_files_architecture (no changes needed)
|
140
|
+
# -----------------------------------------------------------------------------
|
141
|
+
def base_files_architecture(password, score, verdict, file_type):
|
142
|
+
if file_type.lower() in ("json", ".json"):
|
143
|
+
return json.dumps({"password": password, "score": str(score), "veredict": verdict}, indent=4, ensure_ascii=False) + "\n\n"
|
144
|
+
if file_type.lower() in ("csv", ".csv"):
|
145
|
+
return (
|
146
|
+
f'"password","{password}",\n'
|
147
|
+
f'"score","{score}\n"'
|
148
|
+
f'"veredict","{verdict}"\n'
|
149
|
+
) + "\n"
|
150
|
+
if file_type.lower() in ("yaml", ".yaml", "yml", ".yml"):
|
151
|
+
return (
|
152
|
+
f'"password": "{password}"\n'
|
153
|
+
f'"score": "{score}"\n'
|
154
|
+
f'"veredict": "{verdict}"\n'
|
155
|
+
) + "\n"
|
156
|
+
|
157
|
+
# -----------------------------------------------------------------------------
|
158
|
+
# Function: generator
|
159
|
+
# Description:
|
160
|
+
# Builds possible password permutations based on user info and ciphers,
|
161
|
+
# filters by length, evaluates strength, and saves them
|
162
|
+
# -----------------------------------------------------------------------------
|
163
|
+
|
164
|
+
def generator(
|
165
|
+
name: str,
|
166
|
+
age: str,
|
167
|
+
birth_date: str,
|
168
|
+
file_type: str = "json",
|
169
|
+
file_name: str = "pass_generated"
|
170
|
+
) -> None:
|
171
|
+
dt = datetime.strptime(birth_date, "%d/%m/%Y")
|
172
|
+
day, month, year = dt.strftime("%d"), dt.strftime("m"), dt.strftime("Y")
|
173
|
+
name_tiny = name.lower().replace(" ", "")
|
174
|
+
parts = name.split()
|
175
|
+
first = parts[0]
|
176
|
+
middle = "".join(parts[1:-1]) if len(parts) > 2 else ""
|
177
|
+
last = parts[-1] if len(parts) > 1 else ""
|
178
|
+
age_reversed = age[::-1]
|
179
|
+
bases = [
|
180
|
+
name_tiny, name.upper().replace(" ", ""), first, middle, last,
|
181
|
+
day, month, year, age, age_reversed,
|
182
|
+
apply_ciphers(name_tiny), apply_ciphers(first), apply_ciphers(last)
|
183
|
+
]
|
184
|
+
bases = list({b for b in bases if b.strip()})
|
185
|
+
possible_passwords = set()
|
186
|
+
total = sum(perm(len(bases), r) for r in range(2, 5))
|
187
|
+
with Progress(
|
188
|
+
TextColumn("[cyan]Generating passwords..."),
|
189
|
+
BarColumn(),
|
190
|
+
TimeElapsedColumn(),
|
191
|
+
) as progress:
|
192
|
+
task = progress.add_task("passwords", total=total)
|
193
|
+
for length in range(2, 5):
|
194
|
+
for combo in itertools.permutations(bases, length):
|
195
|
+
pwd = "".join(combo)
|
196
|
+
if 6 <= len(pwd) <= 18:
|
197
|
+
possible_passwords.add(pwd)
|
198
|
+
progress.update(task, advance=1)
|
199
|
+
scored = [(pwd, verify(pwd, False), veredict(verify(pwd, False))) for pwd in possible_passwords]
|
200
|
+
passwords, scores, verdicts = zip(*scored)
|
201
|
+
save_to_file(list(passwords), list(scores), list(verdicts), file_name, file_type)
|
202
|
+
|
203
|
+
# -----------------------------------------------------------------------------
|
204
|
+
# Sequence, verdict, and verify unchanged (except typo fix)
|
205
|
+
# -----------------------------------------------------------------------------
|
206
|
+
|
207
|
+
def check_sequences(password: str) -> bool:
|
208
|
+
digits = [int(c) for c in password if c.isdigit()]
|
209
|
+
for i in range(len(digits) - 2):
|
210
|
+
if digits[i] + 1 == digits[i+1] == digits[i+2] - 1:
|
211
|
+
return True
|
212
|
+
if digits[i] - 1 == digits[i+1] == digits[i+2] + 1:
|
213
|
+
return True
|
214
|
+
return False
|
215
|
+
|
216
|
+
def veredict(score: int) -> str:
|
217
|
+
levels = [
|
218
|
+
"#very_weak", "#weak", "#weak", "#mean", "#good", "#strong", "#very_strong"
|
219
|
+
]
|
220
|
+
return levels[score] if 0 <= score < len(levels) else "#unknown"
|
221
|
+
|
222
|
+
def verify(
|
223
|
+
password: str,
|
224
|
+
want_verdict: bool = True,
|
225
|
+
) -> int | str:
|
226
|
+
strength = 0
|
227
|
+
if len(password) >= 8:
|
228
|
+
strength += 1
|
229
|
+
if re.search(r'\d', password):
|
230
|
+
strength += 1
|
231
|
+
if any(c in string.punctuation for c in password):
|
232
|
+
strength += 1
|
233
|
+
if any(c.isupper() for c in password):
|
234
|
+
strength += 1
|
235
|
+
if any(c.islower() for c in password):
|
236
|
+
strength += 1
|
237
|
+
if not check_sequences(password):
|
238
|
+
strength += 1
|
239
|
+
return veredict(strength) if want_verdict else strength
|