diff --git a/README.md b/README.md index bd63795..938fad7 100644 --- a/README.md +++ b/README.md @@ -2,10 +2,13 @@

safelock-cli - + build status + + + linter badge - Go Reference + Go Reference

@@ -61,6 +64,7 @@ You can find interactive examples of using it as a package to [encrypt](https:// |-------------------------|---------------------------------------------| | Iterations | 3 | | Memory size | 64 Megabytes | +| Salt length | 16 | | Key length | 32 | | Threads | Number of available cores `runtime.NumCPU()`| | Minimum password length | 8 | diff --git a/benchmark/bench_and_plot.py b/benchmark/bench_and_plot.py index be90b30..b7bb6be 100644 --- a/benchmark/bench_and_plot.py +++ b/benchmark/bench_and_plot.py @@ -5,7 +5,7 @@ import matplotlib.pyplot as plt from matplotlib.colors import XKCD_COLORS as plot_colors -safelock_cmd = "safelock-cli" +safelock_cmd = "~/Projects/safelock-cli/safelock-cli" pwd = "123456789" rest = "60s" input_path = "Videos" @@ -13,26 +13,20 @@ output_dir = "safelock_dump" runs = 3 figure_width = 14 -figure_height = 2.5 -bar_width = 0.6 +figure_height = 2.3 +bar_width = 0.65 measure = "Seconds" root = os.getcwd() -def get_label(i, clean=False, key="command"): +def get_label(i, key="command"): matchers = [ ('gpg', 'gpgtar',), ('7z', '7zip (fastest)',), ('age', 'age (tar-zstd)'), ('safelock', 'safelock',), ] - label = next((v for m, v in matchers if m in i[key])) - if clean: - return label - if key == "label": - return f"{label}\n{i['size']:.2f} MB" - - return f"{label}\n{i['median']:.3f}s" + return next((v for m, v in matchers if m in i[key])) def get_name(i): matchers = [ @@ -48,8 +42,8 @@ def encrypt(): err = os.system( f"hyperfine --runs {runs} --prepare " f"'sleep {rest}' " - f"'echo \"{pwd}\" | {safelock_cmd} encrypt {input_path} {get_name('safelock')} --quiet' " f"'tar cv --zstd {input_path} | . {root}/pipe_age_password.sh | age -e -p -o {get_name('age')}' " + f"'echo \"{pwd}\" | {safelock_cmd} encrypt {input_path} {get_name('safelock')} --quiet' " f"'7z a -p{pwd} -mx1 {get_name('7z')} {input_path}' " f"'gpgtar -e -o {get_name('gpg')} -c --yes --batch --gpg-args \"--passphrase {pwd}\" {input_path}' " f"--export-json {root}/encryption.json" @@ -62,8 +56,8 @@ def decrypt(): err = os.system( f"hyperfine --runs {runs} --prepare " f"'rm -rf {output_dir} {output_name}_*_ && mkdir {output_dir} && sleep {rest}' " - f"'echo \"{pwd}\" | {safelock_cmd} decrypt {get_name('safelock')} {output_dir} --quiet' " f"'sleep 0.05; xdotool type \"{pwd}\"; xdotool key \"Return\" | age --decrypt {get_name('age')} | tar x --zstd -f - -C {output_dir}' " + f"'echo \"{pwd}\" | {safelock_cmd} decrypt {get_name('safelock')} {output_dir} --quiet' " f"'7z e -y -p{pwd} -mx1 {get_name('7z')} -o{output_dir}' " f"'gpgtar -d --yes --batch --gpg-args \"--passphrase {pwd}\" {get_name('gpg')}' " f"--export-json {root}/decryption.json" @@ -73,8 +67,8 @@ def decrypt(): exit(err) os.chdir(os.path.expanduser("~")) -# encrypt() -# decrypt() +encrypt() +decrypt() os.chdir(root) plt.margins(3.5) @@ -85,16 +79,15 @@ def decrypt(): data = sorted(json.load(f)['results'], key=lambda i: i['median']) labels = [get_label(i) for i in data] scores = [i['median'] for i in data] - colors_map = {get_label(i, 1): random.choice(list(plot_colors.values())) for i in data} - colors = [colors_map[get_label(i, 1)] for i in data] + colors_map = {get_label(i): random.choice(list(plot_colors.values())) for i in data} + colors = [colors_map[get_label(i)] for i in data] fig, ax = plt.subplots() ax.set_title('Encryption Time') ax.set_xlabel(measure) -ax.yaxis.set_label_position('right') -ax.set_ylabel('lower is better') -ax.grid(zorder=0, axis='x', color='black') +ax.grid(zorder=0, axis='x') ax.barh(labels, scores, bar_width, color=colors, zorder=3) +ax.bar_label(ax.containers[0], label_type='edge', padding=3, fmt=lambda i: f"{i:.2f}") fig.set_size_inches(w=figure_width, h=figure_height) fig.tight_layout() fig.savefig("encryption-time.webp", transparent=True, format="webp") @@ -106,15 +99,14 @@ def decrypt(): data = sorted(json.load(f)['results'], key=lambda i: i['median']) labels = [get_label(i) for i in data] decryption = [i['median'] for i in data] - colors = [colors_map[get_label(i, 1)] for i in data] + colors = [colors_map[get_label(i)] for i in data] fig, ax = plt.subplots() ax.set_title('Decryption Time') ax.set_xlabel(measure) -ax.yaxis.set_label_position('right') -ax.set_ylabel('lower is better') -ax.grid(zorder=0, axis='x', color='black') +ax.grid(zorder=0, axis='x') ax.barh(labels, decryption, bar_width, color=colors, zorder=3) +ax.bar_label(ax.containers[0], label_type='edge', padding=3, fmt=lambda i: f"{i:.2f}") fig.set_size_inches(w=figure_width, h=figure_height) fig.tight_layout() fig.savefig("decryption-time.webp", transparent=True, format="webp") @@ -126,20 +118,19 @@ def decrypt(): data = sorted([{ 'size': os.path.getsize(get_name(get_label(i))) / 1024 / 1024, 'label': get_label(i), - 'color': colors_map[get_label(i, 1)], + 'color': colors_map[get_label(i)], } for i in data], key=lambda i: i['size']) os.chdir(root) -labels = [get_label(i, key='label') for i in data] +labels = [get_label(i, 'label') for i in data] sizes = [i['size'] for i in data] colors = [i['color'] for i in data] fig, ax = plt.subplots() ax.set_title('File Size') -ax.set_xlabel("Megabytes") -ax.yaxis.set_label_position('right') -ax.set_ylabel('lower is better') -ax.grid(zorder=0, axis='x', color='black') +ax.set_xlabel("MegaBytes") +ax.grid(zorder=0, axis='x') ax.barh(labels, sizes, bar_width, color=colors, zorder=3) +ax.bar_label(ax.containers[0], label_type='edge', padding=3, fmt=lambda i: f"{i:.0f}") fig.set_size_inches(w=figure_width, h=figure_height) fig.tight_layout() fig.savefig("file-size.webp", transparent=True, format="webp") diff --git a/benchmark/decryption-time.webp b/benchmark/decryption-time.webp index 4fa863d..3152b72 100644 Binary files a/benchmark/decryption-time.webp and b/benchmark/decryption-time.webp differ diff --git a/benchmark/decryption.json b/benchmark/decryption.json index 0c13d90..7a8a829 100644 --- a/benchmark/decryption.json +++ b/benchmark/decryption.json @@ -1,18 +1,18 @@ { "results": [ { - "command": "echo \"123456789\" | ~/Projects/safelock-cli/safelock-cli decrypt test.sla safelock_dump --quiet", - "mean": 1.8276349158133336, - "stddev": 0.14566191806696024, - "median": 1.9042654354800002, - "user": 2.309450346666667, - "system": 1.9107805599999999, - "min": 1.6596538664800002, - "max": 1.9189854454800002, + "command": "sleep 0.05; xdotool type \"123456789\"; xdotool key \"Return\" | age --decrypt test.age | tar x --zstd -f - -C safelock_dump", + "mean": 3.2734613258266667, + "stddev": 0.38923582353211417, + "median": 3.30132871616, + "user": 2.7651234999999996, + "system": 6.166127426666666, + "min": 2.87104071616, + "max": 3.64801454516, "times": [ - 1.9189854454800002, - 1.9042654354800002, - 1.6596538664800002 + 3.64801454516, + 2.87104071616, + 3.30132871616 ], "exit_codes": [ 0, @@ -21,18 +21,18 @@ ] }, { - "command": "sleep 0.05; xdotool type \"123456789\"; xdotool key \"Return\" | age --decrypt test.age | tar x --zstd -f - -C safelock_dump", - "mean": 2.816656686146667, - "stddev": 0.2702910723941267, - "median": 2.9378343294800002, - "user": 2.6122993466666666, - "system": 5.240392226666667, - "min": 2.50698103648, - "max": 3.00515469248, + "command": "echo \"123456789\" | ~/Projects/safelock-cli/safelock-cli decrypt test.sla safelock_dump --quiet", + "mean": 2.0015877658266668, + "stddev": 0.006728462206629033, + "median": 2.00485857816, + "user": 2.4911125000000003, + "system": 2.106313093333333, + "min": 1.9938492011600002, + "max": 2.00605551816, "times": [ - 3.00515469248, - 2.9378343294800002, - 2.50698103648 + 2.00605551816, + 1.9938492011600002, + 2.00485857816 ], "exit_codes": [ 0, @@ -42,17 +42,17 @@ }, { "command": "7z e -y -p123456789 -mx1 test.7z -osafelock_dump", - "mean": 18.76303972514667, - "stddev": 0.10991428273642811, - "median": 18.72587103648, - "user": 20.692533679999997, - "system": 1.3673248933333333, - "min": 18.67652879848, - "max": 18.886719340480003, + "mean": 18.780328156826666, + "stddev": 0.09312114686946973, + "median": 18.83279570716, + "user": 20.808235166666666, + "system": 1.4123247599999997, + "min": 18.672811449159997, + "max": 18.83537731416, "times": [ - 18.67652879848, - 18.886719340480003, - 18.72587103648 + 18.83537731416, + 18.83279570716, + 18.672811449159997 ], "exit_codes": [ 0, @@ -62,17 +62,17 @@ }, { "command": "gpgtar -d --yes --batch --gpg-args \"--passphrase 123456789\" test.gpg", - "mean": 6.573486912813334, - "stddev": 0.3839886822791872, - "median": 6.52200845048, - "user": 0.21511468, - "system": 1.4525625599999998, - "min": 6.21783424048, - "max": 6.98061804748, + "mean": 6.849333490159999, + "stddev": 1.0445899571644215, + "median": 6.89337370116, + "user": 0.2077078333333333, + "system": 1.5517317599999998, + "min": 5.78341994016, + "max": 7.87120682916, "times": [ - 6.98061804748, - 6.52200845048, - 6.21783424048 + 6.89337370116, + 7.87120682916, + 5.78341994016 ], "exit_codes": [ 0, diff --git a/benchmark/encryption-time.webp b/benchmark/encryption-time.webp index 6549637..95cff4c 100644 Binary files a/benchmark/encryption-time.webp and b/benchmark/encryption-time.webp differ diff --git a/benchmark/encryption.json b/benchmark/encryption.json index 26ff6a4..1b16dc2 100644 --- a/benchmark/encryption.json +++ b/benchmark/encryption.json @@ -1,18 +1,18 @@ { "results": [ { - "command": "echo \"123456789\" | ~/Projects/safelock-cli/safelock-cli encrypt Videos test.sla --quiet", - "mean": 2.915796215026667, - "stddev": 0.6152785400365611, - "median": 2.59659688136, - "user": 2.9221347666666673, - "system": 1.8123637266666666, - "min": 2.52571277236, - "max": 3.62507899136, + "command": "tar cv --zstd Videos | . ~/Projects/safelock-cli/benchmark/pipe_age_password.sh | age -e -p -o test.age", + "mean": 3.402120916973333, + "stddev": 0.36723519264164584, + "median": 3.5784137606399997, + "user": 3.4905991999999997, + "system": 3.9755335666666665, + "min": 2.97998001664, + "max": 3.64796897364, "times": [ - 3.62507899136, - 2.59659688136, - 2.52571277236 + 3.5784137606399997, + 2.97998001664, + 3.64796897364 ], "exit_codes": [ 0, @@ -21,18 +21,18 @@ ] }, { - "command": "tar cv --zstd Videos | . /home/mrf3/Projects/safelock-cli/benchmark/pipe_age_password.sh | age -e -p -o test.age", - "mean": 3.5844030323599996, - "stddev": 0.8456093581031698, - "median": 3.99741505136, - "user": 3.664084433333333, - "system": 4.025338726666667, - "min": 2.61165881536, - "max": 4.14413523036, + "command": "echo \"123456789\" | ~/Projects/safelock-cli/safelock-cli encrypt Videos test.sla --quiet", + "mean": 3.513391508973333, + "stddev": 0.38369050393747534, + "median": 3.50677411664, + "user": 2.8737848666666665, + "system": 2.7115099, + "min": 3.13305250164, + "max": 3.9003479086399997, "times": [ - 2.61165881536, - 3.99741505136, - 4.14413523036 + 3.50677411664, + 3.9003479086399997, + 3.13305250164 ], "exit_codes": [ 0, @@ -42,17 +42,17 @@ }, { "command": "7z a -p123456789 -mx1 test.7z Videos", - "mean": 20.89819147436, - "stddev": 0.521090452676126, - "median": 20.99556633936, - "user": 144.56984343333332, - "system": 1.0643993933333333, - "min": 20.33528243436, - "max": 21.36372564936, + "mean": 20.72411361464, + "stddev": 0.31234900452082415, + "median": 20.87433041064, + "user": 144.74405119999997, + "system": 1.040940233333333, + "min": 20.365036756640002, + "max": 20.93297367664, "times": [ - 21.36372564936, - 20.33528243436, - 20.99556633936 + 20.87433041064, + 20.365036756640002, + 20.93297367664 ], "exit_codes": [ 0, @@ -62,17 +62,17 @@ }, { "command": "gpgtar -e -o test.gpg -c --yes --batch --gpg-args \"--passphrase 123456789\" Videos", - "mean": 44.73956679669333, - "stddev": 3.0879084948438327, - "median": 44.51365098336, - "user": 34.082144766666666, - "system": 9.58027806, - "min": 41.77082056336, - "max": 47.93422884336, + "mean": 45.75403499330667, + "stddev": 1.37469158193794, + "median": 45.82139649264, + "user": 34.73840786666667, + "system": 10.408470566666665, + "min": 44.346901016640004, + "max": 47.09380747064, "times": [ - 44.51365098336, - 47.93422884336, - 41.77082056336 + 47.09380747064, + 45.82139649264, + 44.346901016640004 ], "exit_codes": [ 0, diff --git a/benchmark/file-size.webp b/benchmark/file-size.webp index 0e4b71c..74730fe 100644 Binary files a/benchmark/file-size.webp and b/benchmark/file-size.webp differ diff --git a/cmd/encrypt.go b/cmd/encrypt.go index f46d37e..32f394b 100644 --- a/cmd/encrypt.go +++ b/cmd/encrypt.go @@ -41,8 +41,9 @@ var encryptCmd = &cobra.Command{ sl.Quiet = beQuiet inputPath, outputPath := []string{args[0]}, args[1] + fileFlags := os.O_RDWR | os.O_CREATE | os.O_TRUNC - if outputFile, err = os.OpenFile(outputPath, os.O_RDWR|os.O_CREATE, 0755); err != nil { + if outputFile, err = os.OpenFile(outputPath, fileFlags, 0755); err != nil { utils.PrintErrsAndExit((&slErrs.ErrInvalidOutputPath{ Path: outputPath, Err: err, diff --git a/cmd/root.go b/cmd/root.go index b632c1d..75f2825 100644 --- a/cmd/root.go +++ b/cmd/root.go @@ -14,7 +14,7 @@ var rootCmd = &cobra.Command{ Use: "safelock-cli", Short: "Simple tool to encrypt/decrypt files with AES encryption", Long: "Simple command-line tool to encrypt and decrypt files with AES encryption", - Version: "0.5.0", + Version: "0.6.0", CompletionOptions: cobra.CompletionOptions{ DisableDefaultCmd: true, },