Skip to content

Commit 91e2d5c

Browse files
author
爱音爱素食
committed
Changed "signature" to "password" for accuracy; implemented custom iterations.
1 parent de2b766 commit 91e2d5c

File tree

3 files changed

+160
-60
lines changed

3 files changed

+160
-60
lines changed

.idea/workspace.xml

Lines changed: 33 additions & 22 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

hook-tkinterdnd2.py

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
"""pyinstaller hook file.
2+
3+
You need to use this hook-file if you are packaging a project using tkinterdnd2.
4+
Just put hook-tkinterdnd2.py in the same directory where you call pyinstaller and type:
5+
6+
pyinstaller myproject/myproject.py --additional-hooks-dir=.
7+
"""
8+
9+
from PyInstaller.utils.hooks import collect_data_files, eval_statement
10+
11+
12+
datas = collect_data_files('tkinterdnd2')

main.py

Lines changed: 115 additions & 38 deletions
Original file line numberDiff line numberDiff line change
@@ -19,8 +19,8 @@
1919
TRANSLATIONS = {
2020
"title": {"en": "Python Encryption Tool (PBKDF2 + AES)", "zh": "Python 加密工具 (PBKDF2 + AES)"},
2121
"control_panel": {"en": "Control Panel", "zh": "控制面板"},
22-
"signature": {"en": "Signature:", "zh": "签名:"},
23-
"confirm_sign": {"en": "Confirm Sign", "zh": "确认签名"},
22+
"password": {"en": "密码:", "zh": "密码:"},
23+
"confirm_pwd": {"en": "confirm pwd", "zh": "确认密码"},
2424
"algorithm": {"en": "Algorithm:", "zh": "算法:"},
2525
"set_enc_out": {"en": "Set Enc Output Dir", "zh": "设置加密输出目录"},
2626
"set_dec_out": {"en": "Set Dec Output Dir", "zh": "设置解密输出目录"},
@@ -40,31 +40,41 @@
4040
"ready": {"en": "Ready", "zh": "就绪"},
4141
"processing": {"en": "Processing...", "zh": "处理中..."},
4242
"done": {"en": "Done!", "zh": "完成!"},
43-
"missing_sig_title": {"en": "Missing Signature", "zh": "缺少签名"},
44-
"missing_sig_msg": {"en": "Please enter a signature first.", "zh": "请先输入签名。"},
45-
"sig_conf_title": {"en": "Signature Confirmed", "zh": "签名已确认"},
46-
"sig_conf_msg": {"en": "Signature captured. PBKDF2 salt will be generated during operations.", "zh": "签名已捕获。PBKDF2 盐值将在操作期间生成。"},
47-
"sig_empty_msg": {"en": "Signature is empty!", "zh": "签名为空!"},
43+
"missing_pwd_title": {"en": "Missing Password", "zh": "缺少密码"},
44+
"missing_pwd_msg": {"en": "Please enter a password first.", "zh": "请先输入密码。"},
45+
"pwd_conf_title": {"en": "Password Confirmed", "zh": "密码已确认"},
46+
"pwd_conf_msg": {"en": "Password captured.", "zh": "密码已捕获。"},
47+
"pwd_empty_msg": {"en": "Password is empty!", "zh": "密码为空!"},
4848
"warning": {"en": "Warning", "zh": "警告"},
4949
"error": {"en": "Error", "zh": "错误"},
5050
"file_error_title": {"en": "File Error", "zh": "文件错误"},
5151
"file_error_msg": {"en": "Invalid input file.", "zh": "无效的输入文件。"},
5252
"op_complete": {"en": "Complete", "zh": "完成"},
5353
"saved_to": {"en": "Saved to:", "zh": "保存至:"},
54-
"dec_fail_msg": {"en": "Decryption failed. Check signature or format.", "zh": "解密失败。请检查签名或格式。"},
55-
"lang_label": {"en": "Language:", "zh": "语言:"}
54+
"dec_fail_msg": {"en": "Decryption failed. Check Password or format.", "zh": "解密失败。请检查密码或格式。"},
55+
"lang_label": {"en": "Language:", "zh": "语言:"},
56+
"iterations": {"en": "Iterations(0<x<100000000):", "zh": "迭代次数(0<x<100000000):"},
57+
"confirm_iterations": {"en": "Confirm Iterations", "zh": "确认迭代次数"},
58+
"missing_iterations_title": {"en": "Missing Iterations", "zh": "缺少迭代次数"},
59+
"missing_iterations_msg": {"en": "Iterations cannot be empty!", "zh": "迭代次数不能为空!"},
60+
"iterations_conf_msg": {"en": "Iterations confirmed.", "zh": "迭代次数已确认。"},
61+
"iterations_empty_msg": {"en": "Iterations is empty!", "zh": "迭代次数为空!"},
62+
"iterations_max_restrict": {"en": "Iterations cannot exceed 100000000!", "zh": "迭代次数不能超过100000000!"},
5663
}
5764

5865
CONFIG_FILE = "settings.json"
5966

6067
class EncryptApp(BaseWindow):
68+
# MAX_ITERATIONS
69+
MAX_ITERATIONS = 100_000_000
6170
def __init__(self):
6271
super().__init__()
6372
self.crypto = CryptoManager()
6473
self.enc_output_path = tk.StringVar()
6574
self.dec_output_path = tk.StringVar()
6675
self.selected_enc_file = tk.StringVar()
6776
self.selected_dec_file = tk.StringVar()
77+
self.iterations_var = tk.StringVar()
6878

6979
self.lang_code = "en"
7080
self.translatable_widgets = [] # List of (widget, key, attribute_name)
@@ -84,6 +94,7 @@ def load_settings(self):
8494
self.enc_output_path.set(settings.get("enc_output_path", ""))
8595
self.dec_output_path.set(settings.get("dec_output_path", ""))
8696
self.lang_code = settings.get("language", "en")
97+
self.iterations_var.set(settings.get("iterations", "100000"))
8798
except Exception as e:
8899
print(f"Failed to load settings: {e}")
89100

@@ -92,7 +103,8 @@ def save_settings(self):
92103
settings = {
93104
"enc_output_path": self.enc_output_path.get(),
94105
"dec_output_path": self.dec_output_path.get(),
95-
"language": self.lang_code
106+
"language": self.lang_code,
107+
"iterations": int(self.iterations_var.get())
96108
}
97109
try:
98110
with open(CONFIG_FILE, 'w', encoding='utf-8') as f:
@@ -157,17 +169,17 @@ def setup_ui(self):
157169
self.register_widget(top_frame, "control_panel", "text")
158170
top_frame.pack(fill="x", padx=10, pady=5)
159171

160-
# Signature
161-
lbl_sig = ttk.Label(top_frame)
162-
self.register_widget(lbl_sig, "signature")
163-
lbl_sig.pack(side="left", padx=5)
172+
# password
173+
lbl_pwd = ttk.Label(top_frame)
174+
self.register_widget(lbl_pwd, "password")
175+
lbl_pwd.pack(side="left", padx=5)
164176

165-
self.sig_entry = ttk.Entry(top_frame, width=20, show="*")
166-
self.sig_entry.pack(side="left", padx=5)
177+
self.pwd_entry = ttk.Entry(top_frame, width=20, show="*")
178+
self.pwd_entry.pack(side="left", padx=5)
167179

168-
self.btn_confirm_sig = ttk.Button(top_frame, command=self.confirm_signature)
169-
self.register_widget(self.btn_confirm_sig, "confirm_sign")
170-
self.btn_confirm_sig.pack(side="left", padx=5)
180+
self.btn_confirm_pwd = ttk.Button(top_frame, command=self.confirm_password)
181+
self.register_widget(self.btn_confirm_pwd, "confirm_pwd")
182+
self.btn_confirm_pwd.pack(side="left", padx=5)
171183

172184
# Algorithm
173185
lbl_algo = ttk.Label(top_frame)
@@ -194,6 +206,19 @@ def setup_ui(self):
194206
self.lang_combo.pack(side="left", padx=5)
195207
self.lang_combo.bind("<<ComboboxSelected>>", self.update_language)
196208

209+
#iterations
210+
lbl_iter = ttk.Label(top_frame)
211+
self.register_widget(lbl_iter, "iterations")
212+
lbl_iter.pack(side="left", padx=5)
213+
214+
self.iter_entry = ttk.Entry(top_frame, width=20, textvariable=self.iterations_var)
215+
self.iter_entry.pack(side="left", padx=5)
216+
217+
self.btn_confirm_iterations = ttk.Button(top_frame, command=self.confirm_iterations)
218+
self.register_widget(self.btn_confirm_iterations, "confirm_iterations")
219+
self.btn_confirm_iterations.pack(side="left", padx=5)
220+
221+
197222
# Output Paths
198223
btn_enc_out = ttk.Button(top_frame, command=self.select_enc_out_dir)
199224
self.register_widget(btn_enc_out, "set_enc_out")
@@ -339,19 +364,65 @@ def log(self, area, message):
339364
area.see("end")
340365
area.config(state="disabled")
341366

342-
def get_signature(self):
343-
sig = self.sig_entry.get()
344-
if not sig:
345-
messagebox.showwarning(self.tr("missing_sig_title"), self.tr("missing_sig_msg"))
367+
def get_password(self):
368+
pwd = self.pwd_entry.get()
369+
if not pwd:
370+
messagebox.showwarning(self.tr("missing_pwd_title"), self.tr("missing_pwd_msg"))
346371
return None
347-
return sig
372+
return pwd
348373

349-
def confirm_signature(self):
350-
sig = self.sig_entry.get()
351-
if sig:
352-
messagebox.showinfo(self.tr("sig_conf_title"), self.tr("sig_conf_msg"))
374+
def confirm_password(self):
375+
pwd = self.pwd_entry.get()
376+
if pwd:
377+
messagebox.showinfo(self.tr("pwd_conf_title"), self.tr("pwd_conf_msg"))
353378
else:
354-
messagebox.showwarning(self.tr("warning"), self.tr("sig_empty_msg"))
379+
messagebox.showwarning(self.tr("warning"), self.tr("pwd_empty_msg"))
380+
381+
def check_iterations(self):
382+
try:
383+
iterations_str = self.iter_entry.get()
384+
if not iterations_str:
385+
messagebox.showwarning(self.tr("missing_iterations_title"), self.tr("missing_iterations_msg"))
386+
return False
387+
388+
iterations = int(iterations_str)
389+
390+
if iterations <= 0:
391+
messagebox.showwarning(self.tr("warning"), self.tr("iterations_empty_msg"))
392+
return False
393+
394+
if iterations > self.MAX_ITERATIONS:
395+
messagebox.showerror(self.tr("error"), self.tr("iterations_max_restrict"))
396+
return False
397+
return True
398+
except ValueError:
399+
messagebox.showerror(self.tr("error"), "Invalid number format!")
400+
return False
401+
402+
def get_iterations(self):
403+
is_valid_iterations = self.check_iterations()
404+
if not is_valid_iterations:
405+
return None
406+
else:
407+
iterations = int(self.iter_entry.get())
408+
if not iterations:
409+
messagebox.showwarning(self.tr("missing_iterations_title"), self.tr("missing_iterations_msg"))
410+
return None
411+
self.crypto.ITERATIONS = iterations
412+
return iterations
413+
414+
def confirm_iterations(self):
415+
is_valid_iterations = self.check_iterations()
416+
if not is_valid_iterations:
417+
return None
418+
else:
419+
iterations = int(self.iter_entry.get())
420+
if iterations:
421+
messagebox.showinfo(self.tr("iterations_conf_title"), self.tr("iterations_conf_msg"))
422+
self.crypto.ITERATIONS = iterations
423+
self.save_settings()
424+
else:
425+
messagebox.showwarning(self.tr("warning"), self.tr("iterations_empty_msg"))
355426

356427
def select_enc_out_dir(self):
357428
d = filedialog.askdirectory()
@@ -370,29 +441,33 @@ def select_file(self, var):
370441
if f: var.set(f)
371442

372443
def action_encrypt_text(self):
373-
sig = self.get_signature()
374-
if not sig: return
444+
pwd = self.get_password()
445+
iterations = self.get_iterations()
446+
if not iterations: return
447+
if not pwd: return
375448

376449
text = self.enc_input.get("1.0", "end-1c")
377450
if not text: return
378451

379452
try:
380453
algo = self.algo_var.get()
381-
result = self.crypto.encrypt_text(text, sig, algo)
454+
result = self.crypto.encrypt_text(text, pwd, algo)
382455
self.log(self.enc_log, f"Encrypted ({algo}):\n{result}")
383456
except Exception as e:
384457
messagebox.showerror(self.tr("error"), str(e))
385458

386459
def action_decrypt_text(self):
387-
sig = self.get_signature()
388-
if not sig: return
460+
pwd = self.get_password()
461+
iterations = self.get_iterations()
462+
if not iterations: return
463+
if not pwd: return
389464

390465
text = self.dec_input.get("1.0", "end-1c")
391466
if not text: return
392467

393468
try:
394469
algo = self.algo_var.get()
395-
result = self.crypto.decrypt_text(text.strip(), sig, algo)
470+
result = self.crypto.decrypt_text(text.strip(), pwd, algo)
396471
self.log(self.dec_log, f"Decrypted ({algo}):\n{result}")
397472
except Exception as e:
398473
self.log(self.dec_log, f"Error: {str(e)}")
@@ -407,8 +482,10 @@ def action_decrypt_file(self):
407482
self.crypto.decrypt_file, self.dec_pb, self.dec_status, ".dec", self.tr("file_dec_title"))
408483

409484
def _run_file_op(self, input_var, output_dir_var, op_func, pb, status_lbl, suffix, op_name):
410-
sig = self.get_signature()
411-
if not sig: return
485+
pwd = self.get_password()
486+
iterations = self.get_iterations()
487+
if not iterations: return
488+
if not pwd: return
412489

413490
in_path = input_var.get()
414491
if not in_path or not os.path.exists(in_path):
@@ -450,7 +527,7 @@ def progress(current, total):
450527
self.after(0, lambda: pb.config(value=perc))
451528

452529
start_time = datetime.datetime.now()
453-
op_func(in_path, out_path, sig, algo, progress)
530+
op_func(in_path, out_path, pwd, algo, progress)
454531
end_time = datetime.datetime.now()
455532

456533
self.after(0, lambda: status_lbl.config(text=f"{str_done} ({end_time - start_time})", foreground="green"))

0 commit comments

Comments
 (0)