# Licence: GNU AGPL v3: http://www.gnu.org/licenses/ # This file is part of [`delarte`](https://git.afpy.org/fcode/delarte.git) """delarte - ArteTV dowloader. usage: delarte [-h|--help] - print this message or: delarte program_page_url - show available versions or: delarte program_page_url version - show available resolutions or: delarte program_page_url version resolution - download the given video """ import sys import time from . import api from . import hls from . import muxing from . import naming from . import www from . import cli def _fail(message, code=1): print(message, file=sys.stderr) return code def _print_available_renditions(config, f): print(f"Available versions:", file=f) for code, label in api.iter_renditions(config): print(f"\t{code} - {label}", file=f) def _print_available_variants(version_index, f): print(f"Available resolutions:", file=f) for code, label in hls.iter_variants(version_index): print(f"\t{code} - {label}", file=f) def create_progress(): """Create a progress handler for input downloads.""" state = { "last_update_time": 0, "last_channel": None, } def progress(channel, current, total): now = time.time() if current == total: print(f"\rDownloading {channel}: 100.0%") state["last_update_time"] = now elif channel != state["last_channel"]: print(f"Dowloading {channel}: 0.0%", end="") state["last_update_time"] = now state["last_channel"] = channel elif now - state["last_update_time"] > 1: print( f"\rDownloading {channel}: {int(1000.0 * current / total) / 10.0}%", end="", ) state["last_update_time"] = now return progress def main(): """CLI command.""" parser = cli.Parser() args = parser.get_args_as_list() if not args or args[0] == "-h" or args[0] == "--help": print(__doc__) return 0 try: www_lang, program_id = www.parse_url(args.pop(0)) except ValueError as e: return _fail(f"Invalid url: {e}") try: config = api.load_config(www_lang, program_id) except ValueError: return _fail("Invalid program") if not args: _print_available_renditions(config, sys.stdout) return 0 master_playlist_url = api.select_rendition(config, args.pop(0)) if master_playlist_url is None: _fail("Invalid version") _print_available_renditions(config, sys.stderr) return 1 master_playlist = hls.load_master_playlist(master_playlist_url) if not args: _print_available_variants(master_playlist, sys.stdout) return 0 remote_inputs = hls.select_variant(master_playlist, args.pop(0)) if remote_inputs is None: _fail("Invalid resolution") _print_available_variants(master_playlist, sys.stderr) return 0 file_base_name = naming.build_file_base_name(config) progress = create_progress() with hls.download_inputs(remote_inputs, progress) as temp_inputs: muxing.mux(temp_inputs, file_base_name, progress) if __name__ == "__main__": sys.exit(main())