skilleter-thingy 0.0.24__tar.gz → 0.0.26__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.
Potentially problematic release.
This version of skilleter-thingy might be problematic. Click here for more details.
- {skilleter_thingy-0.0.24/skilleter_thingy.egg-info → skilleter_thingy-0.0.26}/PKG-INFO +1 -2
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/pyproject.toml +1 -2
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/git_review.py +11 -5
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/photodupe.py +42 -16
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26/skilleter_thingy.egg-info}/PKG-INFO +1 -2
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy.egg-info/SOURCES.txt +0 -2
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy.egg-info/requires.txt +0 -1
- skilleter_thingy-0.0.24/skilleter_thingy/aws.py +0 -548
- skilleter_thingy-0.0.24/skilleter_thingy/s3_sync.py +0 -383
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/LICENSE +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/README.md +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/setup.cfg +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/__init__.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/addpath.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/borger.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/colour.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/console_colours.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/dc_curses.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/dc_defaults.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/dc_util.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/dircolors.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/diskspacecheck.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/docker.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/docker_purge.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/ffind.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/files.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/ggit.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/ggrep.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/git.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/git2.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/git_br.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/git_ca.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/git_cleanup.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/git_co.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/git_common.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/git_hold.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/git_mr.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/git_parent.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/git_update.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/git_wt.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/gitcmp_helper.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/gitlab.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/gitprompt.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/gl.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/gphotosync.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/linecount.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/logger.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/moviemover.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/path.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/phototidier.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/popup.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/process.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/py_audit.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/readable.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/remdir.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/rmdupe.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/rpylint.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/run.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/splitpics.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/strreplace.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/sysmon.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/tfm.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/tfm_pane.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/tfparse.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/tidy.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/trimpath.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/window_rename.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/xchmod.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy/yamlcheck.py +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy.egg-info/dependency_links.txt +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy.egg-info/entry_points.txt +0 -0
- {skilleter_thingy-0.0.24 → skilleter_thingy-0.0.26}/skilleter_thingy.egg-info/top_level.txt +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.1
|
|
2
2
|
Name: skilleter_thingy
|
|
3
|
-
Version: 0.0.
|
|
3
|
+
Version: 0.0.26
|
|
4
4
|
Summary: A collection of useful utilities, mainly aimed at making Git more friendly
|
|
5
5
|
Author-email: John Skilleter <john@skilleter.org.uk>
|
|
6
6
|
Project-URL: Home, https://skilleter.org.uk
|
|
@@ -10,7 +10,6 @@ Classifier: Operating System :: OS Independent
|
|
|
10
10
|
Requires-Python: >=3.6
|
|
11
11
|
Description-Content-Type: text/markdown
|
|
12
12
|
License-File: LICENSE
|
|
13
|
-
Requires-Dist: boto3
|
|
14
13
|
Requires-Dist: imagehash
|
|
15
14
|
Requires-Dist: inotify
|
|
16
15
|
Requires-Dist: pillow
|
|
@@ -7,7 +7,7 @@ name = "skilleter_thingy"
|
|
|
7
7
|
|
|
8
8
|
# Version must be incremented to install updated Thingy
|
|
9
9
|
|
|
10
|
-
version = "0.0.
|
|
10
|
+
version = "0.0.26"
|
|
11
11
|
|
|
12
12
|
authors = [
|
|
13
13
|
{name="John Skilleter", email="john@skilleter.org.uk"},
|
|
@@ -26,7 +26,6 @@ classifiers = [
|
|
|
26
26
|
]
|
|
27
27
|
|
|
28
28
|
dependencies = [
|
|
29
|
-
"boto3",
|
|
30
29
|
"imagehash",
|
|
31
30
|
"inotify",
|
|
32
31
|
"pillow",
|
|
@@ -514,6 +514,12 @@ class GitReview():
|
|
|
514
514
|
def show_file_list(self):
|
|
515
515
|
""" Draw the current page of the file list """
|
|
516
516
|
|
|
517
|
+
def format_change(prefix, value):
|
|
518
|
+
"""If value is 0 just return it as a string, otherwise apply the prefix and
|
|
519
|
+
return it (e.g. '+' or '-')"""
|
|
520
|
+
|
|
521
|
+
return f'{prefix}{value}' if value else '0'
|
|
522
|
+
|
|
517
523
|
for ypos in range(0, self.file_list_h):
|
|
518
524
|
|
|
519
525
|
normal_colour = curses.color_pair(COLOUR_NORMAL)
|
|
@@ -535,13 +541,13 @@ class GitReview():
|
|
|
535
541
|
# Diff stats, with or without non-whitespace changes
|
|
536
542
|
|
|
537
543
|
if self.show_none_whitespace_stats:
|
|
538
|
-
added =
|
|
539
|
-
deleted =
|
|
544
|
+
added = format_change('+', current_file["non-ws added"])
|
|
545
|
+
deleted = format_change('-', current_file["non-ws deleted"])
|
|
540
546
|
else:
|
|
541
|
-
added =
|
|
542
|
-
deleted =
|
|
547
|
+
added = format_change('+', current_file["added"])
|
|
548
|
+
deleted = format_change('-', current_file["deleted"])
|
|
543
549
|
|
|
544
|
-
status = f'{current_file["status"]} {
|
|
550
|
+
status = f'{current_file["status"]} {deleted:>4}/{added:>4}'
|
|
545
551
|
|
|
546
552
|
abspath = os.path.join(self.working_tree_dir, filename)
|
|
547
553
|
|
|
@@ -5,6 +5,7 @@ import sys
|
|
|
5
5
|
import os
|
|
6
6
|
import sys
|
|
7
7
|
import pickle
|
|
8
|
+
import argparse
|
|
8
9
|
|
|
9
10
|
import PIL
|
|
10
11
|
|
|
@@ -15,28 +16,42 @@ import imagehash
|
|
|
15
16
|
|
|
16
17
|
################################################################################
|
|
17
18
|
|
|
18
|
-
def read_image_hashes():
|
|
19
|
+
def read_image_hashes(directories):
|
|
19
20
|
"""Read all the specfied directories and hash every picture therein"""
|
|
20
21
|
|
|
21
22
|
hashes = defaultdict(list)
|
|
22
23
|
|
|
23
|
-
|
|
24
|
+
# Walk each directory tree
|
|
25
|
+
|
|
26
|
+
for directory in directories:
|
|
27
|
+
print(f'Scanning directory tree {directory}')
|
|
28
|
+
|
|
24
29
|
for root, _, files in os.walk(directory):
|
|
30
|
+
print(f'Scanning directory {root}')
|
|
31
|
+
|
|
25
32
|
for file in files:
|
|
26
33
|
filepath = os.path.join(root, file)
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
34
|
+
|
|
35
|
+
fileext = os.path.splitext(file)[1]
|
|
36
|
+
|
|
37
|
+
if fileext.lower() not in ('.jbf', '.ini', '.xml', '.ffs_db'):
|
|
38
|
+
# Calculate the hash and store path, dimensions and file size under the hash entry in the hashes table
|
|
39
|
+
|
|
40
|
+
try:
|
|
41
|
+
with Image.open(filepath) as image:
|
|
42
|
+
hash_value = imagehash.average_hash(image, hash_size=12)
|
|
43
|
+
|
|
44
|
+
size = os.stat(filepath).st_size
|
|
45
|
+
hashes[hash_value].append({'path': filepath, 'width': image.width, 'height': image.height, 'size': size})
|
|
46
|
+
|
|
47
|
+
except PIL.UnidentifiedImageError:
|
|
48
|
+
sys.stderr.write(f'ERROR: Unrecognized format {filepath} (size={size})\n')
|
|
49
|
+
|
|
50
|
+
except OSError:
|
|
51
|
+
sys.stderr.write(f'ERROR: Unable to read {filepath} (size={size})\n')
|
|
52
|
+
|
|
53
|
+
# Return the hash table
|
|
54
|
+
|
|
40
55
|
return hashes
|
|
41
56
|
|
|
42
57
|
################################################################################
|
|
@@ -44,6 +59,15 @@ def read_image_hashes():
|
|
|
44
59
|
def main():
|
|
45
60
|
"""Read the hashes and report duplicates in a vaguely civilised way"""
|
|
46
61
|
|
|
62
|
+
parser = argparse.ArgumentParser(description='Search for similar images')
|
|
63
|
+
parser.add_argument('directories', nargs='*', action='store', help='Directories to search')
|
|
64
|
+
|
|
65
|
+
args = parser.parse_args()
|
|
66
|
+
|
|
67
|
+
if not args.directories:
|
|
68
|
+
print('You must be specify at least one directory')
|
|
69
|
+
sys.exit(1)
|
|
70
|
+
|
|
47
71
|
try:
|
|
48
72
|
print('Loading cached data')
|
|
49
73
|
|
|
@@ -52,8 +76,10 @@ def main():
|
|
|
52
76
|
except (FileNotFoundError, EOFError):
|
|
53
77
|
print('Scanning directories')
|
|
54
78
|
|
|
55
|
-
hashes = read_image_hashes()
|
|
79
|
+
hashes = read_image_hashes(args.directories)
|
|
56
80
|
|
|
81
|
+
# Sort the list of hashes so that we can easily find close matches
|
|
82
|
+
|
|
57
83
|
print('Sorting hashes')
|
|
58
84
|
|
|
59
85
|
hash_values = sorted([str(hashval) for hashval in hashes])
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.1
|
|
2
2
|
Name: skilleter_thingy
|
|
3
|
-
Version: 0.0.
|
|
3
|
+
Version: 0.0.26
|
|
4
4
|
Summary: A collection of useful utilities, mainly aimed at making Git more friendly
|
|
5
5
|
Author-email: John Skilleter <john@skilleter.org.uk>
|
|
6
6
|
Project-URL: Home, https://skilleter.org.uk
|
|
@@ -10,7 +10,6 @@ Classifier: Operating System :: OS Independent
|
|
|
10
10
|
Requires-Python: >=3.6
|
|
11
11
|
Description-Content-Type: text/markdown
|
|
12
12
|
License-File: LICENSE
|
|
13
|
-
Requires-Dist: boto3
|
|
14
13
|
Requires-Dist: imagehash
|
|
15
14
|
Requires-Dist: inotify
|
|
16
15
|
Requires-Dist: pillow
|
|
@@ -3,7 +3,6 @@ README.md
|
|
|
3
3
|
pyproject.toml
|
|
4
4
|
skilleter_thingy/__init__.py
|
|
5
5
|
skilleter_thingy/addpath.py
|
|
6
|
-
skilleter_thingy/aws.py
|
|
7
6
|
skilleter_thingy/borger.py
|
|
8
7
|
skilleter_thingy/colour.py
|
|
9
8
|
skilleter_thingy/console_colours.py
|
|
@@ -50,7 +49,6 @@ skilleter_thingy/remdir.py
|
|
|
50
49
|
skilleter_thingy/rmdupe.py
|
|
51
50
|
skilleter_thingy/rpylint.py
|
|
52
51
|
skilleter_thingy/run.py
|
|
53
|
-
skilleter_thingy/s3_sync.py
|
|
54
52
|
skilleter_thingy/splitpics.py
|
|
55
53
|
skilleter_thingy/strreplace.py
|
|
56
54
|
skilleter_thingy/sysmon.py
|