SickGear/lib/hachoir/metadata/main.py
2023-02-09 13:41:15 +00:00

168 lines
6 KiB
Python

from hachoir.core.error import error
from hachoir.core.i18n import getTerminalCharset
from hachoir.core.benchmark import Benchmark
from hachoir.stream import InputStreamError
from hachoir.core.tools import makePrintable
from hachoir.core.cmd_line import displayVersion
from hachoir.parser import createParser, ParserList
import hachoir.core.config as hachoir_config
from hachoir.metadata import config
from optparse import OptionParser
from hachoir.metadata import extractMetadata
from hachoir.metadata.metadata import extractors as metadata_extractors
import sys
def displayParserList(*args):
parser_list = ParserList()
for parser in list(metadata_extractors.keys()):
parser_list.add(parser)
parser_list.print_("List of metadata extractors.")
sys.exit(0)
def parseOptions():
parser = OptionParser(usage="%prog [options] files")
parser.add_option("--type", help="Only display file type (description)",
action="store_true", default=False)
parser.add_option("--mime", help="Only display MIME type",
action="store_true", default=False)
parser.add_option("--level",
help="Quantity of information to display from 1 to 9 (9 is the maximum)",
action="store", default="9", type="choice",
choices=[str(choice) for choice in range(1, 9 + 1)])
parser.add_option("--raw", help="Raw output",
action="store_true", default=False)
parser.add_option("--bench", help="Run benchmark",
action="store_true", default=False)
parser.add_option("--force-parser", help="List all parsers then exit",
type="str")
parser.add_option("--parser-list", help="List all parsers then exit",
action="callback", callback=displayParserList)
parser.add_option("--profiler", help="Run profiler",
action="store_true", default=False)
parser.add_option("--version", help="Display version and exit",
action="callback", callback=displayVersion)
parser.add_option("--quality", help="Information quality (0.0=fastest, 1.0=best, and default is 0.5)",
action="store", type="float", default="0.5")
parser.add_option("--maxlen", help="Maximum string length in characters, 0 means unlimited (default: %s)" % config.MAX_STR_LENGTH,
type="int", default=config.MAX_STR_LENGTH)
parser.add_option("--verbose", help="Verbose mode",
default=False, action="store_true")
parser.add_option("--debug", help="Debug mode",
default=False, action="store_true")
values, filename = parser.parse_args()
if len(filename) == 0:
parser.print_help()
sys.exit(1)
# Update limits
config.MAX_STR_LENGTH = values.maxlen
if values.raw:
config.RAW_OUTPUT = True
return values, filename
def processFile(values, filename,
display_filename=False, priority=None, human=True, display=True):
charset = getTerminalCharset()
# Create parser
try:
if values.force_parser:
tags = [("id", values.force_parser), None]
else:
tags = None
parser = createParser(filename, tags=tags)
except InputStreamError as err:
error(str(err))
return False
if not parser:
error("Unable to parse file: %s" % filename)
return False
with parser:
# Extract metadata
extract_metadata = not(values.mime or values.type)
if extract_metadata:
try:
metadata = extractMetadata(parser, values.quality)
except Exception as err:
error(str(err))
metadata = None
if not metadata:
parser.error("Hachoir can't extract metadata, but is able to parse: %s"
% filename)
return False
else:
if values.type:
result = parser.description
else:
result = parser.mime_type
if display:
# Display metadatas on stdout
if extract_metadata:
text = metadata.exportPlaintext(priority=priority, human=human)
if not text:
text = ["(no metadata, priority may be too small)"]
if display_filename:
for line in text:
line = "%s: %s" % (filename, line)
print(makePrintable(line, charset))
else:
for line in text:
print(makePrintable(line, charset))
else:
text = result
if display_filename:
text = "%s: %s" % (filename, text)
print(text)
return True
def processFiles(values, filenames, display=True):
human = not(values.raw)
ok = True
priority = int(values.level) * 100 + 99
display_filename = (1 < len(filenames))
for filename in filenames:
ok &= processFile(values, filename, display_filename,
priority, human, display)
return ok
def benchmarkMetadata(values, filenames):
bench = Benchmark()
bench.run(processFiles, values, filenames, display=False)
def profile(values, filenames):
from hachoir.core.profiler import runProfiler
return runProfiler(processFiles, (values, filenames), {'display': False})
def main():
try:
# Parser options and initialize Hachoir
values, filenames = parseOptions()
if values.debug:
hachoir_config.debug = True
elif values.verbose:
hachoir_config.verbose = True
else:
hachoir_config.quiet = True
if values.profiler:
ok = profile(values, filenames)
elif values.bench:
ok = benchmarkMetadata(values, filenames)
else:
ok = processFiles(values, filenames)
except KeyboardInterrupt:
print("Program interrupted (CTRL+C).")
ok = False
sys.exit(int(not ok))