rtty-soda 0.1.5__py3-none-any.whl → 0.2.0__py3-none-any.whl
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.
Potentially problematic release.
This version of rtty-soda might be problematic. Click here for more details.
- rtty_soda/archivers.py +11 -3
- rtty_soda/cli_io.py +65 -28
- rtty_soda/cryptography/kdf.py +12 -5
- rtty_soda/cryptography/public.py +12 -12
- rtty_soda/cryptography/secret.py +13 -10
- rtty_soda/encoders/__init__.py +6 -2
- rtty_soda/encoders/base26_encoder.py +2 -3
- rtty_soda/encoders/base31_encoder.py +16 -0
- rtty_soda/encoders/base36_encoder.py +2 -3
- rtty_soda/encoders/base64_encoder.py +15 -0
- rtty_soda/encoders/base94_encoder.py +2 -3
- rtty_soda/encoders/encoder.py +11 -0
- rtty_soda/encoders/functions.py +3 -1
- rtty_soda/encoders/raw_encoder.py +13 -0
- rtty_soda/main.py +307 -112
- rtty_soda/main.pyi +100 -0
- rtty_soda-0.2.0.dist-info/METADATA +333 -0
- rtty_soda-0.2.0.dist-info/RECORD +23 -0
- {rtty_soda-0.1.5.dist-info → rtty_soda-0.2.0.dist-info}/WHEEL +1 -1
- rtty_soda-0.1.5.dist-info/METADATA +0 -254
- rtty_soda-0.1.5.dist-info/RECORD +0 -18
- {rtty_soda-0.1.5.dist-info → rtty_soda-0.2.0.dist-info}/entry_points.txt +0 -0
rtty_soda/main.py
CHANGED
|
@@ -1,6 +1,3 @@
|
|
|
1
|
-
# ruff: noqa: PLR0913 - not applicable because we don't call Click Commands directly
|
|
2
|
-
# ruff: noqa: ANN201 - not applicable because the Click Commands are untyped
|
|
3
|
-
# mypy: disable-error-code = "no-untyped-def, misc"
|
|
4
1
|
from pathlib import Path
|
|
5
2
|
|
|
6
3
|
import click
|
|
@@ -11,14 +8,13 @@ from rtty_soda.archivers import ARCHIVERS, UNARCHIVERS
|
|
|
11
8
|
from rtty_soda.cli_io import (
|
|
12
9
|
print_stats,
|
|
13
10
|
read_bytes,
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
read_plaintext_bytes,
|
|
11
|
+
read_key_bytes,
|
|
12
|
+
read_password_bytes,
|
|
17
13
|
write_output,
|
|
18
14
|
)
|
|
19
15
|
from rtty_soda.cryptography import public, secret
|
|
20
16
|
from rtty_soda.cryptography.kdf import KDF_PROFILES, kdf
|
|
21
|
-
from rtty_soda.encoders import ENCODERS
|
|
17
|
+
from rtty_soda.encoders import ENCODERS
|
|
22
18
|
|
|
23
19
|
in_path = click.Path(
|
|
24
20
|
exists=True,
|
|
@@ -38,62 +34,129 @@ CONTEXT_SETTINGS = {"help_option_names": ["-h", "--help"]}
|
|
|
38
34
|
|
|
39
35
|
@click.group(cls=ClickAliasedGroup, context_settings=CONTEXT_SETTINGS)
|
|
40
36
|
@click.version_option(package_name="rtty-soda")
|
|
41
|
-
def cli():
|
|
37
|
+
def cli() -> None:
|
|
42
38
|
pass
|
|
43
39
|
|
|
44
40
|
|
|
45
|
-
@cli.command()
|
|
41
|
+
@cli.command() # pyright: ignore[reportAny]
|
|
46
42
|
@click.option("--encoding", "-e", default="base64", show_default=True)
|
|
47
|
-
|
|
43
|
+
@click.option("--output-file", "-o", type=out_path, help="Write output to file.")
|
|
44
|
+
@click.option("--group-len", default=0, show_default=True)
|
|
45
|
+
@click.option("--line-len", default=0, show_default=True)
|
|
46
|
+
@click.option("--padding", default=0, show_default=True)
|
|
47
|
+
def genkey_cmd(
|
|
48
|
+
encoding: str, output_file: Path | None, group_len: int, line_len: int, padding: int
|
|
49
|
+
) -> None:
|
|
48
50
|
"""Generate Private Key.
|
|
49
51
|
|
|
50
|
-
Encoding: base26 | base36 | base64 | base94
|
|
52
|
+
Encoding: base26 | base31 | base36 | base64 | base94 | binary
|
|
51
53
|
"""
|
|
52
54
|
enc = ENCODERS[encoding]
|
|
53
|
-
|
|
54
|
-
click.echo(key.encode(enc))
|
|
55
|
+
is_bin = encoding == "binary"
|
|
55
56
|
|
|
57
|
+
key = bytes(PrivateKey.generate())
|
|
58
|
+
key = enc.encode(key)
|
|
56
59
|
|
|
57
|
-
|
|
60
|
+
write_output(
|
|
61
|
+
target=output_file,
|
|
62
|
+
data=key,
|
|
63
|
+
is_binary=is_bin,
|
|
64
|
+
group_len=group_len,
|
|
65
|
+
line_len=line_len,
|
|
66
|
+
padding=padding,
|
|
67
|
+
)
|
|
68
|
+
|
|
69
|
+
|
|
70
|
+
@cli.command() # pyright: ignore[reportAny]
|
|
58
71
|
@click.argument("private_key_file", type=in_path)
|
|
59
72
|
@click.option("--encoding", "-e", default="base64", show_default=True)
|
|
60
|
-
|
|
73
|
+
@click.option("--output-file", "-o", type=out_path, help="Write output to file.")
|
|
74
|
+
@click.option("--group-len", default=0, show_default=True)
|
|
75
|
+
@click.option("--line-len", default=0, show_default=True)
|
|
76
|
+
@click.option("--padding", default=0, show_default=True)
|
|
77
|
+
def pubkey_cmd(
|
|
78
|
+
private_key_file: Path,
|
|
79
|
+
encoding: str,
|
|
80
|
+
output_file: Path | None,
|
|
81
|
+
group_len: int,
|
|
82
|
+
line_len: int,
|
|
83
|
+
padding: int,
|
|
84
|
+
) -> None:
|
|
61
85
|
"""Get Public Key.
|
|
62
86
|
|
|
63
|
-
Encoding: base26 | base36 | base64 | base94
|
|
87
|
+
Encoding: base26 | base31 | base36 | base64 | base94 | binary
|
|
64
88
|
"""
|
|
65
89
|
enc = ENCODERS[encoding]
|
|
66
|
-
|
|
67
|
-
priv = PrivateKey(key, enc)
|
|
68
|
-
click.echo(priv.public_key.encode(enc))
|
|
90
|
+
is_bin = encoding == "binary"
|
|
69
91
|
|
|
92
|
+
priv = read_key_bytes(source=private_key_file, is_binary=is_bin, encoder=enc)
|
|
93
|
+
priv = PrivateKey(private_key=priv)
|
|
94
|
+
pub = bytes(priv.public_key)
|
|
95
|
+
pub = enc.encode(pub)
|
|
70
96
|
|
|
71
|
-
|
|
97
|
+
write_output(
|
|
98
|
+
target=output_file,
|
|
99
|
+
data=pub,
|
|
100
|
+
is_binary=is_bin,
|
|
101
|
+
group_len=group_len,
|
|
102
|
+
line_len=line_len,
|
|
103
|
+
padding=padding,
|
|
104
|
+
)
|
|
105
|
+
|
|
106
|
+
|
|
107
|
+
@cli.command() # pyright: ignore[reportAny]
|
|
72
108
|
@click.argument("password_file", type=in_path)
|
|
73
109
|
@click.option("--encoding", "-e", default="base64", show_default=True)
|
|
74
110
|
@click.option("--profile", "-p", default="sensitive", show_default=True)
|
|
75
|
-
|
|
111
|
+
@click.option("--output-file", "-o", type=out_path, help="Write output to file.")
|
|
112
|
+
@click.option("--group-len", default=0, show_default=True)
|
|
113
|
+
@click.option("--line-len", default=0, show_default=True)
|
|
114
|
+
@click.option("--padding", default=0, show_default=True)
|
|
115
|
+
def kdf_cmd(
|
|
116
|
+
password_file: Path,
|
|
117
|
+
encoding: str,
|
|
118
|
+
profile: str,
|
|
119
|
+
output_file: Path | None,
|
|
120
|
+
group_len: int,
|
|
121
|
+
line_len: int,
|
|
122
|
+
padding: int,
|
|
123
|
+
) -> None:
|
|
76
124
|
"""Key Derivation Function.
|
|
77
125
|
|
|
78
|
-
Encoding: base26 | base36 | base64 | base94
|
|
126
|
+
Encoding: base26 | base31 | base36 | base64 | base94 | binary
|
|
79
127
|
|
|
80
128
|
Profile: interactive | moderate | sensitive
|
|
81
129
|
"""
|
|
82
130
|
enc = ENCODERS[encoding]
|
|
83
131
|
prof = KDF_PROFILES[profile]
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
132
|
+
is_bin = encoding == "binary"
|
|
133
|
+
|
|
134
|
+
pw = read_password_bytes(password_file)
|
|
135
|
+
key = kdf(password=pw, profile=prof)
|
|
136
|
+
key = enc.encode(key)
|
|
137
|
+
|
|
138
|
+
write_output(
|
|
139
|
+
target=output_file,
|
|
140
|
+
data=key,
|
|
141
|
+
is_binary=is_bin,
|
|
142
|
+
group_len=group_len,
|
|
143
|
+
line_len=line_len,
|
|
144
|
+
padding=padding,
|
|
145
|
+
)
|
|
87
146
|
|
|
88
147
|
|
|
89
|
-
@cli.command(aliases=["e"])
|
|
148
|
+
@cli.command(aliases=["e"]) # pyright: ignore[reportAny]
|
|
90
149
|
@click.argument("private_key_file", type=in_path)
|
|
91
150
|
@click.argument("public_key_file", type=in_path)
|
|
92
151
|
@click.argument("message_file", type=in_path)
|
|
93
152
|
@click.option("--key-encoding", default="base64", show_default=True)
|
|
94
153
|
@click.option("--data-encoding", "-e", default="base64", show_default=True)
|
|
95
|
-
@click.option("--compression", "-c", default="
|
|
96
|
-
@click.option("--output-file", "-o", type=out_path, help="
|
|
154
|
+
@click.option("--compression", "-c", default="zstd", show_default=True)
|
|
155
|
+
@click.option("--output-file", "-o", type=out_path, help="Write output to file.")
|
|
156
|
+
@click.option("--group-len", default=0, show_default=True)
|
|
157
|
+
@click.option("--line-len", default=0, show_default=True)
|
|
158
|
+
@click.option("--padding", default=0, show_default=True)
|
|
159
|
+
@click.option("--verbose", "-v", is_flag=True, help="Show verbose output.")
|
|
97
160
|
def encrypt_public_cmd(
|
|
98
161
|
private_key_file: Path,
|
|
99
162
|
public_key_file: Path,
|
|
@@ -102,34 +165,57 @@ def encrypt_public_cmd(
|
|
|
102
165
|
data_encoding: str,
|
|
103
166
|
compression: str,
|
|
104
167
|
output_file: Path | None,
|
|
105
|
-
|
|
168
|
+
group_len: int,
|
|
169
|
+
line_len: int,
|
|
170
|
+
padding: int,
|
|
171
|
+
verbose: bool,
|
|
172
|
+
) -> None:
|
|
106
173
|
"""Encrypt Message (Public).
|
|
107
174
|
|
|
108
|
-
Encoding: base26 | base36 | base64 | base94 | binary
|
|
175
|
+
Encoding: base26 | base31 | base36 | base64 | base94 | binary
|
|
109
176
|
|
|
110
|
-
Compression: zlib | bz2 | lzma | raw
|
|
177
|
+
Compression: zstd | zlib | bz2 | lzma | raw
|
|
111
178
|
"""
|
|
112
179
|
key_enc = ENCODERS[key_encoding]
|
|
113
180
|
data_enc = ENCODERS[data_encoding]
|
|
114
181
|
archiver = ARCHIVERS[compression]
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
182
|
+
is_bin_key = key_encoding == "binary"
|
|
183
|
+
is_bin_data = data_encoding == "binary"
|
|
184
|
+
|
|
185
|
+
priv = read_key_bytes(
|
|
186
|
+
source=private_key_file, is_binary=is_bin_key, encoder=key_enc
|
|
187
|
+
)
|
|
188
|
+
priv = PrivateKey(private_key=priv)
|
|
189
|
+
pub = read_key_bytes(source=public_key_file, is_binary=is_bin_key, encoder=key_enc)
|
|
190
|
+
pub = PublicKey(public_key=pub)
|
|
191
|
+
data = stats = message_file.read_bytes()
|
|
120
192
|
data = archiver(data)
|
|
121
|
-
data = public.encrypt(private=priv, public=pub, data=data
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
193
|
+
data = public.encrypt(private=priv, public=pub, data=data)
|
|
194
|
+
data = data_enc.encode(data)
|
|
195
|
+
|
|
196
|
+
write_output(
|
|
197
|
+
target=output_file,
|
|
198
|
+
data=data,
|
|
199
|
+
is_binary=is_bin_data,
|
|
200
|
+
group_len=group_len,
|
|
201
|
+
line_len=line_len,
|
|
202
|
+
padding=padding,
|
|
203
|
+
)
|
|
204
|
+
if verbose:
|
|
205
|
+
print_stats(plaintext=stats, ciphertext=data)
|
|
206
|
+
|
|
207
|
+
|
|
208
|
+
@cli.command(aliases=["es"]) # pyright: ignore[reportAny]
|
|
127
209
|
@click.argument("key_file", type=in_path)
|
|
128
210
|
@click.argument("message_file", type=in_path)
|
|
129
211
|
@click.option("--key-encoding", default="base64", show_default=True)
|
|
130
212
|
@click.option("--data-encoding", "-e", default="base64", show_default=True)
|
|
131
|
-
@click.option("--compression", "-c", default="
|
|
132
|
-
@click.option("--output-file", "-o", type=out_path, help="
|
|
213
|
+
@click.option("--compression", "-c", default="zstd", show_default=True)
|
|
214
|
+
@click.option("--output-file", "-o", type=out_path, help="Write output to file.")
|
|
215
|
+
@click.option("--group-len", default=0, show_default=True)
|
|
216
|
+
@click.option("--line-len", default=0, show_default=True)
|
|
217
|
+
@click.option("--padding", default=0, show_default=True)
|
|
218
|
+
@click.option("--verbose", "-v", is_flag=True, help="Show verbose output.")
|
|
133
219
|
def encrypt_secret_cmd(
|
|
134
220
|
key_file: Path,
|
|
135
221
|
message_file: Path,
|
|
@@ -137,31 +223,52 @@ def encrypt_secret_cmd(
|
|
|
137
223
|
data_encoding: str,
|
|
138
224
|
compression: str,
|
|
139
225
|
output_file: Path | None,
|
|
140
|
-
|
|
226
|
+
group_len: int,
|
|
227
|
+
line_len: int,
|
|
228
|
+
padding: int,
|
|
229
|
+
verbose: bool,
|
|
230
|
+
) -> None:
|
|
141
231
|
"""Encrypt Message (Secret).
|
|
142
232
|
|
|
143
|
-
Encoding: base26 | base36 | base64 | base94 | binary
|
|
233
|
+
Encoding: base26 | base31 | base36 | base64 | base94 | binary
|
|
144
234
|
|
|
145
|
-
Compression: zlib | bz2 | lzma | raw
|
|
235
|
+
Compression: zstd | zlib | bz2 | lzma | raw
|
|
146
236
|
"""
|
|
147
237
|
key_enc = ENCODERS[key_encoding]
|
|
148
238
|
data_enc = ENCODERS[data_encoding]
|
|
149
239
|
archiver = ARCHIVERS[compression]
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
data = archiver(data)
|
|
153
|
-
data = secret.encrypt(key=key, data=data, key_enc=key_enc, out_enc=data_enc)
|
|
154
|
-
write_output(output_file, data, data_enc)
|
|
155
|
-
print_stats(stats, data)
|
|
240
|
+
is_bin_key = key_encoding == "binary"
|
|
241
|
+
is_bin_data = data_encoding == "binary"
|
|
156
242
|
|
|
157
|
-
|
|
158
|
-
|
|
243
|
+
key = read_key_bytes(source=key_file, is_binary=is_bin_key, encoder=key_enc)
|
|
244
|
+
data = stats = message_file.read_bytes()
|
|
245
|
+
data = archiver(data)
|
|
246
|
+
data = secret.encrypt(key=key, data=data)
|
|
247
|
+
data = data_enc.encode(data)
|
|
248
|
+
|
|
249
|
+
write_output(
|
|
250
|
+
target=output_file,
|
|
251
|
+
data=data,
|
|
252
|
+
is_binary=is_bin_data,
|
|
253
|
+
group_len=group_len,
|
|
254
|
+
line_len=line_len,
|
|
255
|
+
padding=padding,
|
|
256
|
+
)
|
|
257
|
+
if verbose:
|
|
258
|
+
print_stats(plaintext=stats, ciphertext=data)
|
|
259
|
+
|
|
260
|
+
|
|
261
|
+
@cli.command(aliases=["ep"]) # pyright: ignore[reportAny]
|
|
159
262
|
@click.argument("password_file", type=in_path)
|
|
160
263
|
@click.argument("message_file", type=in_path)
|
|
161
264
|
@click.option("--kdf-profile", "-p", default="sensitive", show_default=True)
|
|
162
265
|
@click.option("--data-encoding", "-e", default="base64", show_default=True)
|
|
163
|
-
@click.option("--compression", "-c", default="
|
|
164
|
-
@click.option("--output-file", "-o", type=out_path, help="
|
|
266
|
+
@click.option("--compression", "-c", default="zstd", show_default=True)
|
|
267
|
+
@click.option("--output-file", "-o", type=out_path, help="Write output to file.")
|
|
268
|
+
@click.option("--group-len", default=0, show_default=True)
|
|
269
|
+
@click.option("--line-len", default=0, show_default=True)
|
|
270
|
+
@click.option("--padding", default=0, show_default=True)
|
|
271
|
+
@click.option("--verbose", "-v", is_flag=True, help="Show verbose output.")
|
|
165
272
|
def encrypt_password_cmd(
|
|
166
273
|
password_file: Path,
|
|
167
274
|
message_file: Path,
|
|
@@ -169,35 +276,53 @@ def encrypt_password_cmd(
|
|
|
169
276
|
data_encoding: str,
|
|
170
277
|
compression: str,
|
|
171
278
|
output_file: Path | None,
|
|
172
|
-
|
|
279
|
+
group_len: int,
|
|
280
|
+
line_len: int,
|
|
281
|
+
padding: int,
|
|
282
|
+
verbose: bool,
|
|
283
|
+
) -> None:
|
|
173
284
|
"""Encrypt Message (Password).
|
|
174
285
|
|
|
175
286
|
KDF profile: interactive | moderate | sensitive
|
|
176
287
|
|
|
177
|
-
Encoding: base26 | base36 | base64 | base94 | binary
|
|
288
|
+
Encoding: base26 | base31 | base36 | base64 | base94 | binary
|
|
178
289
|
|
|
179
|
-
Compression: zlib | bz2 | lzma | raw
|
|
290
|
+
Compression: zstd | zlib | bz2 | lzma | raw
|
|
180
291
|
"""
|
|
181
292
|
prof = KDF_PROFILES[kdf_profile]
|
|
182
293
|
data_enc = ENCODERS[data_encoding]
|
|
183
294
|
archiver = ARCHIVERS[compression]
|
|
184
|
-
|
|
185
|
-
key = kdf(pw, prof, RawEncoder)
|
|
186
|
-
data = stats = read_plaintext_bytes(message_file, data_enc)
|
|
187
|
-
data = archiver(data)
|
|
188
|
-
data = secret.encrypt(key=key, data=data, key_enc=RawEncoder, out_enc=data_enc)
|
|
189
|
-
write_output(output_file, data, data_enc)
|
|
190
|
-
print_stats(stats, data)
|
|
191
|
-
|
|
295
|
+
is_bin_data = data_encoding == "binary"
|
|
192
296
|
|
|
193
|
-
|
|
297
|
+
pw = read_password_bytes(password_file)
|
|
298
|
+
key = kdf(password=pw, profile=prof)
|
|
299
|
+
data = stats = message_file.read_bytes()
|
|
300
|
+
data = archiver(data)
|
|
301
|
+
data = secret.encrypt(key=key, data=data)
|
|
302
|
+
data = data_enc.encode(data)
|
|
303
|
+
|
|
304
|
+
write_output(
|
|
305
|
+
target=output_file,
|
|
306
|
+
data=data,
|
|
307
|
+
is_binary=is_bin_data,
|
|
308
|
+
group_len=group_len,
|
|
309
|
+
line_len=line_len,
|
|
310
|
+
padding=padding,
|
|
311
|
+
)
|
|
312
|
+
if verbose:
|
|
313
|
+
print_stats(plaintext=stats, ciphertext=data)
|
|
314
|
+
|
|
315
|
+
|
|
316
|
+
@cli.command(aliases=["d"]) # pyright: ignore[reportAny]
|
|
194
317
|
@click.argument("private_key_file", type=in_path)
|
|
195
318
|
@click.argument("public_key_file", type=in_path)
|
|
196
319
|
@click.argument("message_file", type=in_path)
|
|
197
320
|
@click.option("--key-encoding", default="base64", show_default=True)
|
|
198
321
|
@click.option("--data-encoding", "-e", default="base64", show_default=True)
|
|
199
|
-
@click.option("--compression", "-c", default="
|
|
200
|
-
@click.option("--output-file", "-o", type=out_path, help="
|
|
322
|
+
@click.option("--compression", "-c", default="zstd", show_default=True)
|
|
323
|
+
@click.option("--output-file", "-o", type=out_path, help="Write output to file.")
|
|
324
|
+
@click.option("--padding", default=0, show_default=True)
|
|
325
|
+
@click.option("--verbose", "-v", is_flag=True, help="Show verbose output.")
|
|
201
326
|
def decrypt_public_cmd(
|
|
202
327
|
private_key_file: Path,
|
|
203
328
|
public_key_file: Path,
|
|
@@ -206,34 +331,53 @@ def decrypt_public_cmd(
|
|
|
206
331
|
data_encoding: str,
|
|
207
332
|
compression: str,
|
|
208
333
|
output_file: Path | None,
|
|
209
|
-
|
|
334
|
+
padding: int,
|
|
335
|
+
verbose: bool,
|
|
336
|
+
) -> None:
|
|
210
337
|
"""Decrypt Message (Public).
|
|
211
338
|
|
|
212
|
-
Encoding: base26 | base36 | base64 | base94 | binary
|
|
339
|
+
Encoding: base26 | base31 | base36 | base64 | base94 | binary
|
|
213
340
|
|
|
214
|
-
Compression: zlib | bz2 | lzma | raw
|
|
341
|
+
Compression: zstd | zlib | bz2 | lzma | raw
|
|
215
342
|
"""
|
|
216
343
|
key_enc = ENCODERS[key_encoding]
|
|
217
344
|
data_enc = ENCODERS[data_encoding]
|
|
218
345
|
unarchiver = UNARCHIVERS[compression]
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
346
|
+
is_bin_key = key_encoding == "binary"
|
|
347
|
+
is_bin_data = data_encoding == "binary"
|
|
348
|
+
|
|
349
|
+
priv = read_key_bytes(
|
|
350
|
+
source=private_key_file, is_binary=is_bin_key, encoder=key_enc
|
|
351
|
+
)
|
|
352
|
+
priv = PrivateKey(private_key=priv)
|
|
353
|
+
pub = read_key_bytes(source=public_key_file, is_binary=is_bin_key, encoder=key_enc)
|
|
354
|
+
pub = PublicKey(public_key=pub)
|
|
355
|
+
data = stats = read_bytes(source=message_file, is_binary=is_bin_data)
|
|
356
|
+
data = data_enc.decode(data)
|
|
357
|
+
data = public.decrypt(private=priv, public=pub, data=data)
|
|
225
358
|
data = unarchiver(data)
|
|
226
|
-
|
|
227
|
-
|
|
359
|
+
|
|
360
|
+
write_output(
|
|
361
|
+
target=output_file,
|
|
362
|
+
data=data,
|
|
363
|
+
is_binary=True,
|
|
364
|
+
group_len=0,
|
|
365
|
+
line_len=0,
|
|
366
|
+
padding=padding,
|
|
367
|
+
)
|
|
368
|
+
if verbose:
|
|
369
|
+
print_stats(plaintext=data, ciphertext=stats)
|
|
228
370
|
|
|
229
371
|
|
|
230
|
-
@cli.command(aliases=["ds"])
|
|
372
|
+
@cli.command(aliases=["ds"]) # pyright: ignore[reportAny]
|
|
231
373
|
@click.argument("key_file", type=in_path)
|
|
232
374
|
@click.argument("message_file", type=in_path)
|
|
233
375
|
@click.option("--key-encoding", default="base64", show_default=True)
|
|
234
376
|
@click.option("--data-encoding", "-e", default="base64", show_default=True)
|
|
235
|
-
@click.option("--compression", "-c", default="
|
|
236
|
-
@click.option("--output-file", "-o", type=out_path, help="
|
|
377
|
+
@click.option("--compression", "-c", default="zstd", show_default=True)
|
|
378
|
+
@click.option("--output-file", "-o", type=out_path, help="Write output to file.")
|
|
379
|
+
@click.option("--padding", default=0, show_default=True)
|
|
380
|
+
@click.option("--verbose", "-v", is_flag=True, help="Show verbose output.")
|
|
237
381
|
def decrypt_secret_cmd(
|
|
238
382
|
key_file: Path,
|
|
239
383
|
message_file: Path,
|
|
@@ -241,31 +385,48 @@ def decrypt_secret_cmd(
|
|
|
241
385
|
data_encoding: str,
|
|
242
386
|
compression: str,
|
|
243
387
|
output_file: Path | None,
|
|
244
|
-
|
|
388
|
+
padding: int,
|
|
389
|
+
verbose: bool,
|
|
390
|
+
) -> None:
|
|
245
391
|
"""Decrypt Message (Secret).
|
|
246
392
|
|
|
247
|
-
Encoding: base26 | base36 | base64 | base94 | binary
|
|
393
|
+
Encoding: base26 | base31 | base36 | base64 | base94 | binary
|
|
248
394
|
|
|
249
|
-
Compression: zlib | bz2 | lzma | raw
|
|
395
|
+
Compression: zstd | zlib | bz2 | lzma | raw
|
|
250
396
|
"""
|
|
251
397
|
key_enc = ENCODERS[key_encoding]
|
|
252
398
|
data_enc = ENCODERS[data_encoding]
|
|
253
399
|
unarchiver = UNARCHIVERS[compression]
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
400
|
+
is_bin_key = key_encoding == "binary"
|
|
401
|
+
is_bin_data = data_encoding == "binary"
|
|
402
|
+
|
|
403
|
+
key = read_key_bytes(source=key_file, is_binary=is_bin_key, encoder=key_enc)
|
|
404
|
+
data = stats = read_bytes(source=message_file, is_binary=is_bin_data)
|
|
405
|
+
data = data_enc.decode(data)
|
|
406
|
+
data = secret.decrypt(key=key, data=data)
|
|
257
407
|
data = unarchiver(data)
|
|
258
|
-
write_output(output_file, data, data_enc)
|
|
259
|
-
print_stats(data, stats)
|
|
260
408
|
|
|
409
|
+
write_output(
|
|
410
|
+
target=output_file,
|
|
411
|
+
data=data,
|
|
412
|
+
is_binary=True,
|
|
413
|
+
group_len=0,
|
|
414
|
+
line_len=0,
|
|
415
|
+
padding=padding,
|
|
416
|
+
)
|
|
417
|
+
if verbose:
|
|
418
|
+
print_stats(plaintext=data, ciphertext=stats)
|
|
261
419
|
|
|
262
|
-
|
|
420
|
+
|
|
421
|
+
@cli.command(aliases=["dp"]) # pyright: ignore[reportAny]
|
|
263
422
|
@click.argument("password_file", type=in_path)
|
|
264
423
|
@click.argument("message_file", type=in_path)
|
|
265
424
|
@click.option("--kdf-profile", "-p", default="sensitive", show_default=True)
|
|
266
425
|
@click.option("--data-encoding", "-e", default="base64", show_default=True)
|
|
267
|
-
@click.option("--compression", "-c", default="
|
|
268
|
-
@click.option("--output-file", "-o", type=out_path, help="
|
|
426
|
+
@click.option("--compression", "-c", default="zstd", show_default=True)
|
|
427
|
+
@click.option("--output-file", "-o", type=out_path, help="Write output to file.")
|
|
428
|
+
@click.option("--padding", default=0, show_default=True)
|
|
429
|
+
@click.option("--verbose", "-v", is_flag=True, help="Show verbose output.")
|
|
269
430
|
def decrypt_password_cmd(
|
|
270
431
|
password_file: Path,
|
|
271
432
|
message_file: Path,
|
|
@@ -273,45 +434,79 @@ def decrypt_password_cmd(
|
|
|
273
434
|
data_encoding: str,
|
|
274
435
|
compression: str,
|
|
275
436
|
output_file: Path | None,
|
|
276
|
-
|
|
437
|
+
padding: int,
|
|
438
|
+
verbose: bool,
|
|
439
|
+
) -> None:
|
|
277
440
|
"""Decrypt Message (Password).
|
|
278
441
|
|
|
279
442
|
KDF profile: interactive | moderate | sensitive
|
|
280
443
|
|
|
281
|
-
Encoding: base26 | base36 | base64 | base94 | binary
|
|
444
|
+
Encoding: base26 | base31 | base36 | base64 | base94 | binary
|
|
282
445
|
|
|
283
|
-
Compression: zlib | bz2 | lzma | raw
|
|
446
|
+
Compression: zstd | zlib | bz2 | lzma | raw
|
|
284
447
|
"""
|
|
285
448
|
prof = KDF_PROFILES[kdf_profile]
|
|
286
449
|
data_enc = ENCODERS[data_encoding]
|
|
287
450
|
unarchiver = UNARCHIVERS[compression]
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
451
|
+
is_bin_data = data_encoding == "binary"
|
|
452
|
+
|
|
453
|
+
pw = read_password_bytes(password_file)
|
|
454
|
+
key = kdf(password=pw, profile=prof)
|
|
455
|
+
data = stats = read_bytes(source=message_file, is_binary=is_bin_data)
|
|
456
|
+
data = data_enc.decode(data)
|
|
457
|
+
data = secret.decrypt(key=key, data=data)
|
|
292
458
|
data = unarchiver(data)
|
|
293
|
-
|
|
294
|
-
|
|
459
|
+
|
|
460
|
+
write_output(
|
|
461
|
+
target=output_file,
|
|
462
|
+
data=data,
|
|
463
|
+
is_binary=True,
|
|
464
|
+
group_len=0,
|
|
465
|
+
line_len=0,
|
|
466
|
+
padding=padding,
|
|
467
|
+
)
|
|
468
|
+
if verbose:
|
|
469
|
+
print_stats(plaintext=data, ciphertext=stats)
|
|
295
470
|
|
|
296
471
|
|
|
297
|
-
@cli.command()
|
|
472
|
+
@cli.command() # pyright: ignore[reportAny]
|
|
298
473
|
@click.argument("in_encoding")
|
|
299
474
|
@click.argument("out_encoding")
|
|
300
475
|
@click.argument("file", type=in_path)
|
|
301
|
-
@click.option("--output-file", "-o", type=out_path, help="
|
|
476
|
+
@click.option("--output-file", "-o", type=out_path, help="Write output to file.")
|
|
477
|
+
@click.option("--group-len", default=0, show_default=True)
|
|
478
|
+
@click.option("--line-len", default=0, show_default=True)
|
|
479
|
+
@click.option("--padding", default=0, show_default=True)
|
|
302
480
|
def encode_cmd(
|
|
303
|
-
in_encoding: str,
|
|
304
|
-
|
|
481
|
+
in_encoding: str,
|
|
482
|
+
out_encoding: str,
|
|
483
|
+
file: Path,
|
|
484
|
+
output_file: Path | None,
|
|
485
|
+
group_len: int,
|
|
486
|
+
line_len: int,
|
|
487
|
+
padding: int,
|
|
488
|
+
) -> None:
|
|
305
489
|
"""Encode File.
|
|
306
490
|
|
|
307
|
-
Encoding: base26 | base36 | base64 | base94 | binary
|
|
491
|
+
Encoding: base26 | base31 | base36 | base64 | base94 | binary
|
|
308
492
|
"""
|
|
309
493
|
in_enc = ENCODERS[in_encoding]
|
|
310
494
|
out_enc = ENCODERS[out_encoding]
|
|
311
|
-
|
|
495
|
+
in_bin = in_encoding == "binary"
|
|
496
|
+
out_bin = out_encoding == "binary"
|
|
497
|
+
|
|
498
|
+
data = read_bytes(source=file, is_binary=in_bin)
|
|
312
499
|
data = in_enc.decode(data)
|
|
313
500
|
data = out_enc.encode(data)
|
|
314
|
-
|
|
501
|
+
|
|
502
|
+
write_output(
|
|
503
|
+
target=output_file,
|
|
504
|
+
data=data,
|
|
505
|
+
is_binary=out_bin,
|
|
506
|
+
group_len=group_len,
|
|
507
|
+
line_len=line_len,
|
|
508
|
+
padding=padding,
|
|
509
|
+
)
|
|
315
510
|
|
|
316
511
|
|
|
317
512
|
if __name__ == "__main__":
|