Sorry, your browser cannot access this site
This page requires browser support (enable) JavaScript
Learn more >

用Python写了一个自动解码的软件,可以自动进行多轮的base 32,58,64,91,二进制以及hex解码。

(后续可能会更新。)

效果

image-20250511205756362

如果可以成功解码成text,则直接输出text:

image-20250511210356484

如果不能,则输出hex作为保底:

image-20250511205815476

代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
import tkinter as tk
from tkinter import scrolledtext
import base64
import re
import base58
import base91


def is_binary(s):
return all(c in '01' for c in s) and len(s) % 8 == 0


def decode_bytes(byte_data):
try:
text = byte_data.decode('utf-8')
return text, True
except UnicodeDecodeError:
return byte_data.hex(), False


def looks_like_base64(s):
return len(s) % 4 == 0 and re.fullmatch(r'[A-Za-z0-9+/=]+', s) is not None


def looks_like_base32(s):
return len(s) % 8 == 0 and re.fullmatch(r'[A-Z2-7=]+', s, re.IGNORECASE) is not None


def looks_like_base58(s):
return all(c in base58.alphabet.decode() for c in s)


def looks_like_base91(s):
return all(33 <= ord(c) <= 126 for c in s)


def try_decode(s, func):
decoded = func(s)
return decode_bytes(decoded)


def recursive_decode(s, path=None, all_paths=None, max_depth=10):
if path is None:
path = []
if all_paths is None:
all_paths = []
if len(path) >= max_depth:
return all_paths

decoders = [
('Base64', looks_like_base64, base64.b64decode),
('Base32', looks_like_base32, base64.b32decode),
('Base58', looks_like_base58, base58.b58decode),
('Base91', looks_like_base91, base91.decode),
('Binary', is_binary, lambda x: bytes(int(x[i:i+8], 2) for i in range(0, len(x), 8))),
('Hex', lambda x: True, lambda x: bytes.fromhex(x)),
]

for name, detector, func in decoders:
if detector(s):
try:
text, is_utf8 = try_decode(s, func)
except Exception:
continue
mode = '(UTF-8)' if is_utf8 else '(hex)'
new_path = path + [(name, text, mode)]
all_paths.append(new_path)
if is_utf8:
recursive_decode(text, new_path, all_paths, max_depth)
return all_paths


def select_final_path(paths):
utf_paths = [p for p in paths if p[-1][2] == '(UTF-8)']
if utf_paths:
max_len = max(len(p) for p in utf_paths)
for p in utf_paths:
if len(p) == max_len:
return p
max_len = max(len(p) for p in paths)
for p in paths:
if len(p) == max_len:
return p


def decode_input():
raw = input_text.get('1.0', tk.END).strip().replace(' ', '')
output_text.delete('1.0', tk.END)
if not raw:
return

paths = recursive_decode(raw)
if not paths:
output_text.insert(tk.END, '无法识别或解码此内容。')
return

final = select_final_path(paths)
for i, (name, text, mode) in enumerate(final, 1):
output_text.insert(tk.END, f"第{i}步 - {name} {mode}\n结果:{text}\n\n")

# 如果只有一步且为 UTF-8,但结果仍可能是编码串,则额外尝试一次解码并输出 hex
if len(final) == 1 and final[0][2] == '(UTF-8)':
s = final[0][1]
extra_decoders = [
('Base64', looks_like_base64, base64.b64decode),
('Base32', looks_like_base32, base64.b32decode),
('Base58', looks_like_base58, base58.b58decode),
('Base91', looks_like_base91, base91.decode),
('Binary', is_binary, lambda x: bytes(int(x[i:i+8], 2) for i in range(0, len(x), 8)))
]
for name, detector, func in extra_decoders:
if detector(s):
try:
data = func(s)
hex_out = data.hex()
output_text.insert(tk.END, f"第2步 - {name} (hex)\n结果:{hex_out}\n")
break
except Exception:
continue

# GUI
root = tk.Tk()
root.title('解码器')
root.geometry('600x500')
font_title = ('微软雅黑', 12, 'bold')
font_text = ('微软雅黑', 10)

tk.Label(root, text='请输入编码内容:', font=font_title).pack(pady=(10,0))
input_text = scrolledtext.ScrolledText(root, height=6, font=font_text, wrap=tk.WORD)
input_text.pack(fill=tk.BOTH, padx=20, pady=5, expand=True)
tk.Button(root, text='开始解码', font=font_title, bg='#4CAF50', fg='white', command=decode_input).pack(pady=10)
tk.Label(root, text='解码输出:', font=font_title).pack()
output_text = scrolledtext.ScrolledText(root, height=10, font=font_text, wrap=tk.WORD)
output_text.pack(fill=tk.BOTH, padx=20, pady=5, expand=True)
root.mainloop()

打包

可以用pyinstaller将这个程序打包成.exe软件。

如果没有安装,则运行:

1
pip install pyinstaller

安装好后运行(先将当前python脚本保存为decoder.py):

1
pyinstaller --noconfirm --windowed --onefile .\decoder.py

.exe文件应该会生成在当前目录下的:

1
dist/decoder.exe

测试

随机生成一段进行过多轮base编码的内容:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
import base64
import base58
import random

text = "hello world"
data = text.encode('utf-8')

encodings = ['base64', 'base32', 'base58']

history = []

for i in range(10):
encoding = random.choice(encodings)
history.append(encoding)

if encoding == 'base64':
data = base64.b64encode(data)
elif encoding == 'base32':
data = base64.b32encode(data)
elif encoding == 'base58':
data = base58.b58encode(data)

print("Final encoded result:", data.decode('utf-8'))
print("Encoding history:", history)

# Final encoded result: VlRKek1WWldTbFphUmxwU1RWWktUVlJyVWt0U2JGRjRXa1ZXVm1FeVVsQlZha1pYVld4YVZsUnJUbFJoTUhCaFZtMXpkMlZzVWtkUmF6RlNWbTE0VmxWNlFYaFVSbHBYVVd0T1dGWnNXa1ZXTW5SUFUxWktObFpzYUZkV1YwNDJWbFJDVjFWRk5WZGhSVnBWVm14d1ZGWXhWWGhXTVZKV1YydG9WV0V3TlZaV1JFWmhVbFpLY2xac1pGWk5SRVpLVlcxd1MxTkdVbGRYYkZKVFZsUldVRlpGVmxOV1JsWnlWVmhzVldFelFsQlZiRkpUVjJ4VmVHSkZPVlZoTWxKSlZtcEdTMVV4Vm5KUFZtUlNUVVp3VTFZeFVrdFVRVDA5
# Encoding history: ['base64', 'base64', 'base32', 'base58', 'base58', 'base32', 'base64', 'base64', 'base64', 'base64']

程序的输出为:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
第1步 - Base64 (UTF-8)
结果:VTJzMVZWSlZaRlpSTVZKTVRrUktSbFF4WkVWVmEyUlBVakZXVWxaVlRrTlRhMHBhVm1zd2VsUkdRazFSVm14VlV6QXhURlpXUWtOWFZsWkVWMnRPU1ZKNlZsaFdWV042VlRCV1VFNVdhRVpVVmxwVFYxVXhWMVJWV2toVWEwNVZWREZhUlZKclZsZFZNREZKVW1wS1NGUldXbFJTVlRWUFZFVlNWRlZyVVhsVWEzQlBVbFJTV2xVeGJFOVVhMlJJVmpGS1UxVnJPVmRSTUZwU1YxUktUQT09

第2步 - Base64 (UTF-8)
结果:U2s1VVJVZFZRMVJMTkRKRlQxZEVVa2RPUjFWUlZVTkNTa0paVmswelRGQk1RVmxVUzAxTFZWQkNXVlZEV2tOSVJ6VlhWVWN6VTBWUE5WaEZUVlpTV1UxV1RVWkhUa05VVDFaRVJrVldVMDFJUmpKSFRWWlRSVTVPVEVSVFVrUXlUa3BPUlRSWlUxbE9Ua2RIVjFKU1VrOVdRMFpSV1RKTA==

第3步 - Base64 (UTF-8)
结果:Sk5URUdVQ1RLNDJFT1dEUkdOR1VRVUNCSkJZVk0zTFBMQVlUS01LVVBCWVVDWkNIRzVXVUczU0VPNVhFTVZSWU1WTUZHTkNUT1ZERkVWU01IRjJHTVZTRU5OTERTUkQyTkpORTRZU1lOTkdHV1JSUk9WQ0ZRWTJL

第4步 - Base64 (UTF-8)
结果:JNTEGUCTK42EOWDRGNGUQUCBJBYVM3LPLAYTKMKUPBYUCZCHG5WUG3SEO5XEMVRYMVMFGNCTOVDFEVSMHF2GMVSENNLDSRD2NJNE4YSYNNGGWRRROVCFQY2K

第5步 - Base32 (UTF-8)
结果:KfCPSW4GXq3MHPAHqVmoX151TxqAdG7mCnDwnFV8eXS4SuFRVL9tfVDkV9DzjZNbXkLkF1uDXcJ

第6步 - Base58 (UTF-8)
结果:4npCTEQcUgxRUY2DRDCpq4jmaCGw8BXZ557XUXvaYf6cK63oEYV1SwW

第7步 - Base58 (UTF-8)
结果:LFKWIV3DGJFEQT2HMRVU22TMGVMWWZCSKBIT2PI=

第8步 - Base32 (UTF-8)
结果:YUdWc2JHOGdkMjl5YkdRPQ==

第9步 - Base64 (UTF-8)
结果:aGVsbG8gd29ybGQ=

第10步 - Base64 (UTF-8)
结果:hello world