From 06ed0c2735141dac2c9d68ba442b82bd4555f7da Mon Sep 17 00:00:00 2001 From: glubsy Date: Sun, 21 Jul 2024 16:27:44 +0200 Subject: [PATCH] Add max-simultaneous-streams parameter --- README.md | 20 ++++++++++++++----- livestream_saver/livestream_saver.py | 29 +++++++++++++++++----------- 2 files changed, 33 insertions(+), 16 deletions(-) diff --git a/README.md b/README.md index cadeeb7..a92baa4 100644 --- a/README.md +++ b/README.md @@ -27,26 +27,32 @@ Basic usage example: `python livestream_saver.py monitor --cookies /path/to/cook ``` > python3 livestream_saver.py monitor --help -usage: livestream_saver.py monitor [-h] [--log-level {DEBUG,INFO,WARNING,ERROR,CRITICAL}] [-c CONFIG_FILE] [--cookies COOKIES_PATH] [-q MAX_VIDEO_QUALITY] [-o OUTPUT_DIR] [--channel-name CHANNEL_NAME] [-s SECTION] [-d] [-n] [-k] [--scan-delay SCAN_DELAY] [--email-notifications] [--skip-download] [YOUTUBE_CHANNEL_URL] +usage: livestream_saver.py monitor [-h] [--log-level {DEBUG,INFO,WARNING,ERROR,CRITICAL}] [-c CONFIG_FILE] [--cookies COOKIES_PATH] [-q MAX_VIDEO_QUALITY] [-o OUTPUT_DIR] + [--channel-name CHANNEL_NAME] [-s SECTION] [-d] [-n] [-k] [--scan-delay SCAN_DELAY] [--email-notifications] [--skip-download] + [--ignore-quality-change] [--max-simultaneous-streams MAX_SIMULTANEOUS_STREAMS] + [YOUTUBE_CHANNEL_URL] positional arguments: YOUTUBE_CHANNEL_URL The Youtube channel to monitor for live streams. Either a full youtube URL, /channel/ID, or /c/name format. (default: None) -optional arguments: +options: -h, --help show this help message and exit --log-level {DEBUG,INFO,WARNING,ERROR,CRITICAL} Log level. (Default: INFO) -c CONFIG_FILE, --config-file CONFIG_FILE Path to config file to use. (Default: ~/.config/livestream_saver/livestream_saver.cfg) - --cookies COOKIES_PATH Path to Netscape formatted cookies file. + --cookies COOKIES_PATH + Path to Netscape formatted cookies file. -q MAX_VIDEO_QUALITY, --max-video-quality MAX_VIDEO_QUALITY - Use best available video resolution up to this height in pixels. Example: "360" for maximum height 360p. Get the highest available resolution by default. + Use best available video resolution up to this height in pixels. Example: "360" for maximum height 360p. Get the highest available resolution by + default. -o OUTPUT_DIR, --output-dir OUTPUT_DIR Output directory where to save channel data. (Default: CWD) --channel-name CHANNEL_NAME User-defined name of the channel to monitor. Will fallback to channel ID deduced from the URL otherwise. -s SECTION, --section SECTION - Override values from the section [monitor NAME] found in config file. If none is specified, will load the first section in config with that name pattern. (default: None) + Override values from the section [monitor NAME] found in config file. If none is specified, will load the first section in config with that name + pattern. (default: None) -d, --delete-source Delete source segment files once the final merging of them has been done. (default: False) -n, --no-merge Do not merge segments after live streams has ended. (default: False) -k, --keep-concat Keep concatenated intermediary files even if merging of streams has been successful. Only useful for troubleshooting. (default: False) @@ -55,6 +61,10 @@ optional arguments: --email-notifications Enables sending e-mail reports to administrator. (Default: False) --skip-download Skip the download phase (useful to run hook scripts instead). (Default: False) + --ignore-quality-change + If stream resolution changes during live-stream, keep downloading anyway. (Default: False) + --max-simultaneous-streams MAX_SIMULTANEOUS_STREAMS + If more than one stream is being broadcast, download up to this number of videos simultaneously. (Default: 2) ``` # Downloading a live stream diff --git a/livestream_saver/livestream_saver.py b/livestream_saver/livestream_saver.py index 99ad2e3..dc6aa03 100644 --- a/livestream_saver/livestream_saver.py +++ b/livestream_saver/livestream_saver.py @@ -31,8 +31,10 @@ NOTIFIER = NotificationDispatcher() +TIME_VARIANCE = 3.0 # in minutes +MAX_SIMULTANEOUS_LIVE_DOWNLOAD = 2 -# HACK forcing use of yt-dlp for the time being. +# HACK forcing use of yt-dlp for the time being. 2024/02 use_ytdl = True @@ -149,7 +151,16 @@ def parse_args(config) -> argparse.Namespace: help='If stream resolution changes during live-stream, keep downloading anyway.'\ f' (Default: {config.getboolean("monitor", "ignore_quality_change")})' ) - + monitor_parser.add_argument('--max-simultaneous-streams', + action='store', + type=int, + default=argparse.SUPPRESS, + help=( + 'If more than one stream is being broadcast, download up to this ' + 'number of videos simultaneously.' + f' (Default: {MAX_SIMULTANEOUS_LIVE_DOWNLOAD})' + ) + ) # Sub-command "download" download_parser = subparsers.add_parser('download', @@ -481,10 +492,6 @@ def _get_target_params( return params -TIME_VARIANCE = 3.0 # in minutes -# TODO allow configuration by user -MAX_SIMULTANEOUS_LIVE_DOWNLOAD = 2 - video_queue: Queue[VideoPost] = Queue(maxsize=4) video_processing = set() video_processed = set() @@ -510,9 +517,9 @@ def video_feeder(queue: Queue, channel: YoutubeChannel, scan_delay: float): def download_task( - video: VideoPost, - config: ConfigParser, - args: Dict, + video: VideoPost, + config: ConfigParser, + args: Dict, session: YoutubeUrllibSession ): if video in video_processing or video in video_processed: @@ -522,7 +529,7 @@ def download_task( video_id = video.get("videoId") # Build the full "/watch?v=..." URL - video_url = f"https://www.youtube.com{video.get('url')}" + video_url = f"https://www.youtube.com{video.get('url')}" if not video_id: try: @@ -655,7 +662,7 @@ def monitor_mode(config: ConfigParser, args: Dict[str, Any]): log.info(f"Monitoring channel: {channel._id}") feeder_thread = threading.Thread( - target=video_feeder, + target=video_feeder, args=(video_queue, channel, scan_delay) ) feeder_thread.daemon = True