File: check_images.py

package info (click to toggle)
blender-doc 4.3-1
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid, trixie
  • size: 253,604 kB
  • sloc: python: 13,030; javascript: 322; makefile: 113; sh: 107
file content (111 lines) | stat: -rwxr-xr-x 3,012 bytes parent folder | download
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
#!/usr/bin/env python3
# Apache License, Version 2.0

"""
This utility checks image paths:

- Are correct and exist.
- Are all used.
"""

import sys
import os
import re


# if you want to operate on a subdir, e.g: "render"
SUBDIR = ""
CURRENT_DIR = os.path.abspath(os.path.dirname(__file__))
ROOT_DIR = os.path.normpath(os.path.join(CURRENT_DIR, "..", ".."))
RST_DIR = os.path.join(ROOT_DIR, "manual", SUBDIR)
LOCALE_DIR = os.path.join(ROOT_DIR, "locale")

# -----------------------------------------------------------------------------
# Common Utilities


def files_recursive(path, ext_test):
    for dirpath, dirnames, filenames in os.walk(path):
        if dirpath.startswith("."):
            continue

        for filename in filenames:
            ext = os.path.splitext(filename)[1]
            if ext.lower().endswith(ext_test):
                yield os.path.join(dirpath, filename)


def print_title(title, underline="="):
    print(f"\n{title.upper()}\n{len(title) * underline}")


# -----------------------------------------------------------------------------
# Global Variables

# .. |SomeID| image:: /images/some_image.png
# .. image:: /images/some_image.png
# .. figure:: /images/some_image.png
#
# note: no checks for commented text currently.
# groups: (1) ID, (2) image name & extension

image_regex = re.compile(
    r"\.\.\s+"
    # |SomeID|  (optional)
    r"(?:\|([a-zA-Z0-9\-_]+)\|\s+)?"
    # figure/image::
    r"(?:figure|image)\:\:\s+"
    # image path
    r"/images/(.*?\.(?:png|gif|jpg|jpeg|svg|webp))",
    re.MULTILINE
)

# -----------------------------------------------------------------------------
# Find Unused/Missing Images


def rst_images(fn, data_src):
    for match in re.finditer(image_regex, data_src):
        yield match.group(2)


def rst_files_report(img_refs):
    """
    Outputs the results of unused/missing images
    """
    imgpath = os.path.normpath(os.path.join(ROOT_DIR, "manual", "images"))
    img_files_set = set([f for f in os.listdir(imgpath)])
    img_refs_set = set(img_refs)

    print_title("List of unused images:")
    for fn in sorted(img_files_set - img_refs_set):
        print(" git rm manual/images/%s" % fn)

    print_title("List of missing images:")
    for fn in sorted(img_refs_set - img_files_set):
        print(fn)

    if len(img_files_set) != len(set([fn.lower() for fn in img_files_set])):
        img_files_set_lower = set()
        print_title("List of case-colliding images:")
        for fn in sort(img_files_set):
            fn_lower = fn.lower()
            if fn_lower in img_files_set_lower:
                print(fn)
            img_files_set_lower.add(fn_lower)


def main():
    if "--help" in sys.argv:
        print(__doc__)
        sys.exit(0)

    rst_file_list = []
    for fn in files_recursive(RST_DIR, ext_test=".rst"):
        with open(fn, "r", encoding="utf-8") as f:
            rst_file_list.extend(rst_images(fn, f.read()))
    rst_files_report(rst_file_list)


if __name__ == "__main__":
    main()