Files

99 lines
2.9 KiB
Python
Raw Permalink Normal View History

#!/usr/bin/env python3
"""Unified entry point for the NCMR songs-videos helper tools.
Dispatches to a sibling script, forwards all remaining arguments, and keeps the
exit status. Use whichever feels natural — this dispatcher, or the script
directly.
python3 scripts/tools.py --help
python3 scripts/tools.py hwprobe
python3 scripts/tools.py tools lrc2srt song.lrc -o song.srt
The same thing, called directly:
python3 scripts/hwprobe.py
"""
from __future__ import annotations
import os
import runpy
import sys
HERE = os.path.dirname(os.path.abspath(__file__))
#: name -> (module filename, one-line summary)
TOOLS: dict[str, tuple[str, str]] = {
"hwprobe": ("hwprobe.py", "which ffmpeg encoders this machine can actually use"),
"ffmpeg": ("ffmpeg_tools.py", "mux, bake subtitles, build still-image videos, strip audio"),
"lrc2srt": ("lrc2srt.py", "convert LRC lyrics to SRT"),
"srt2ass": ("srt2ass.py", "convert SRT subtitles to ASS"),
"bom": ("bom_gen.py", "generate the untracked-asset bill of materials"),
}
ALIASES = {
"ffmpeg_tools": "ffmpeg",
"ffmpeg-tools": "ffmpeg",
"bom_gen": "bom",
"lrc": "lrc2srt",
"srt": "srt2ass",
}
def usage(stream=sys.stdout) -> None:
print("usage: tools.py <tool> [options] [-- <tool options>]", file=stream)
print(" tools.py --help | --list", file=stream)
print(file=stream)
print("tools:", file=stream)
width = max(len(name) for name in TOOLS)
for name, (_filename, summary) in TOOLS.items():
print(f" {name.ljust(width)} {summary}", file=stream)
print(file=stream)
print("Every tool also runs standalone: python3 scripts/<name>.py --help", file=stream)
def main(argv: list[str] | None = None) -> int:
argv = list(sys.argv[1:] if argv is None else argv)
if not argv or argv[0] in ("-h", "--help", "help", "list", "--list"):
usage(stream=sys.stderr if not argv else sys.stdout)
return 0 if argv else 2
name = ALIASES.get(argv[0], argv[0])
if name not in TOOLS:
print(f"tools.py: unknown tool {argv[0]!r}", file=sys.stderr)
print(file=sys.stderr)
usage(stream=sys.stderr)
return 2
filename, _summary = TOOLS[name]
path = os.path.join(HERE, filename)
if not os.path.isfile(path):
print(f"tools.py: {filename} is missing from {HERE}", file=sys.stderr)
return 1
remaining = argv[1:]
if remaining and remaining[0] == "--":
remaining = remaining[1:]
sys.argv = [path, *remaining]
# run_path gives the child the same process, so its exit code is ours.
try:
runpy.run_path(path, run_name="__main__")
except SystemExit as exc:
code = exc.code
if code is None:
return 0
if isinstance(code, int):
return code
print(code, file=sys.stderr)
return 1
return 0
if __name__ == "__main__":
raise SystemExit(main())