Command Palette

Search for a command to run...

Playlists

Playlists & Multi-Video Downloads

fetchit can download entire YouTube playlists, multi-post Threads threads, Instagram carousels, and any URL that yt-dlp recognises as containing more than one video. This guide covers every aspect of playlist handling — from detection and interactive selection to parallel downloading, output structure, and scripting.

How playlist detection works

When you pass a URL to fetchit, it does not assume it is a single video. Instead, it runs a two-phase detection process.

The probing phase

fetchit hands the URL to yt-dlp with the --dump-json flag and inspects the response. The key signal is whether yt-dlp returns an array of entries (a playlist) or a single entry (a standalone video). If the response contains a playlist_id and a non-empty entries array with more than one item, fetchit switches into playlist mode.

The probe extracts the following playlist-level metadata:

  • Playlist title — used as the folder name for output
  • Playlist ID — internal identifier (e.g. PL... for YouTube)
  • Entry count — total number of videos in the playlist
  • Per-entry metadata — title, duration, thumbnail, and format availability for each video
  • Uploader — channel or creator name

Probing a large playlist (100+ videos) can take several seconds because yt-dlp must fetch metadata for every entry. fetchit shows a spinner with a live count of entries discovered so you know progress is happening.

What triggers playlist mode

Playlist mode activates automatically for any URL that yt-dlp recognises as containing multiple videos. This includes:

SourceURL patternBehaviour
YouTube playlistyoutube.com/playlist?list=PL...Full playlist with all entries
YouTube channel / useryoutube.com/@ChannelName or youtube.com/c/...All uploads from the channel
YouTube mixyoutube.com/watch?v=...&list=RD...Auto-generated mix playlist
Threads threadthreads.net/@user/post/... (multi-image)All images/videos in the post
Instagram carouselinstagram.com/p/... (multi-media)All items in the carousel
Bilibili seriesbilibili.com/...series...Series episodes
Twitch collectiontwitch.tv/collections/...Collection of VODs

If the URL contains exactly one video, fetchit proceeds in single-video mode and the format picker appears as usual. There is no way to force playlist mode for a single-video URL, and no way to suppress playlist mode for a multi-video URL — detection is automatic.

What is NOT a playlist

The following URL types are intentionally treated as single videos even though they may appear in playlist-like contexts:

URL typeReason
youtube.com/watch?v=... (single)Only one video ID — no playlist context
youtu.be/...Short link always points to a single video
youtube.com/shorts/...Shorts are standalone short-form videos
instagram.com/reel/...Reels are single videos, not carousels
tiktok.com/@user/video/...TikTok URLs are always single videos
x.com/user/status/... (single media)Single-video tweets download as one file
youtube.com/watch?v=...&list=...Treats only the specific video unless --playlist flag used
If you pass a YouTube URL with both a video ID and a list parameter (youtube.com/watch?v=...&list=...), fetchit fetches just that one video by default. To download the full playlist, extract the playlist URL alone (youtube.com/playlist?list=...).

Interactive playlist mode

When a playlist is detected and you run fetchit without --best or other scriptable flags, you enter interactive playlist mode. This provides a full TUI experience for reviewing and selecting which items to download.

The checklist interface

After probing completes, fetchit displays a scrollable checklist of every video in the playlist. Each entry shows:

  • Index number — the video's position in the playlist (01, 02, 03...)
  • Title — the video title as reported by yt-dlp
  • Duration — length of the video in MM:SS or HH:MM:SS format
  • Checkbox — a [✓] or [ ] indicator showing selection state

All videos are selected by default. The footer displays the total count and the number of currently selected items (e.g., 15/20 selected).

Navigating the checklist

KeyAction
[↑] / [↓]Move selection highlight up/down
[Space]Toggle selection of the highlighted item
[A]Select all items
[N]Deselect all items (none)
[R]Invert selection (reverse current selection)
[PageUp] / [PageDown]Scroll by one page
[Home]Jump to the first item
[End]Jump to the last item
[Enter]Proceed to format selection with the current selection
[Esc]Go back to the input screen

The selection is preserved as you scroll — you can selectively toggle individual videos on and off before committing. This is useful when a playlist contains 50 videos and you only want the 3 relevant ones.

Format selection for multiple videos

After confirming your selection with [Enter], fetchit enters the format picker phase. Unlike single-video mode where you pick one format for one video, here you pick a single format that applies to every selected video in the batch.

The format picker behaves identically to single-video mode — same metadata columns, same sorting, same keyboard shortcuts. However, there are a few important differences:

  • The file size column shows the estimated size per video, not the total batch size
  • Formats that are not available across all selected videos are flagged with a warning icon
  • If a format is unavailable for a particular video, fetchit falls back to the next-best compatible format for that one video and prints a notice
  • Chapter toggling and time range clipping apply to every video in the batch uniformly
Because the same format is applied to all videos, choose a resolution that is available on every item. For example, if most videos have 4K but one is capped at 1080p, selecting 4K will downgrade that one video to its best available format automatically.

Batch download progress

Once you select a format, fetchit begins downloading all selected items. The download screen shows:

  • Overall progress bar — tracks how many videos are complete out of the total selected (e.g., 3/10)
  • Current video progress bar — the per-video download indicator with speed, ETA, and percentage
  • Current video title — shown above the progress bar so you know which item is downloading
  • Elapsed time — total time since the batch started
  • Estimated time remaining — calculated from average download speed and remaining items

When a video finishes, fetchit increments the completed count, logs the saved file path, and immediately starts the next item. There is no pause between downloads unless you press [Esc].

Cancelling a batch

Press [Esc] once to cancel the current video download. The partially downloaded file is deleted and fetchit moves to the next video. Press [Esc] twice quickly to cancel the entire batch — remaining videos are skipped and you return to the format picker.

Scriptable playlist mode

For automation and non-interactive use, fetchit supports downloading playlists entirely from the command line. Every video in the playlist is downloaded automatically with no prompts.

Basic scriptable download

CLI
fetchit --best https://www.youtube.com/playlist?list=PL...
fetchit --mp3 https://www.youtube.com/playlist?list=PL...
fetchit https://www.youtube.com/playlist?list=PL... 1080p

In scriptable mode, the checklist interface is skipped entirely. All videos are selected by default and the specified format is applied uniformly across all entries.

Downloading specific items by index

Use the --items flag to download only specific videos from the playlist. This accepts individual indices, comma-separated lists, and ranges.

CLI
fetchit --best --items 1,3,5 https://youtube.com/playlist?list=PL...
fetchit --best --items 1-10 https://youtube.com/playlist?list=PL...
fetchit --best --items 1-5,8,11-15 https://youtube.com/playlist?list=PL...
SyntaxMeaningExample
NSingle item at index N--items 5
N,M,OMultiple specific items--items 2,7,9
N-MRange from N to M inclusive--items 3-8
N-M,P,Q-RCombination of ranges and singles--items 1-5,10,12-15

Download latest N videos

Use --last to download only the most recent N videos from the playlist. This is useful for catching up on a channel without redownloading everything.

CLI
fetchit --best --last 5 https://youtube.com/playlist?list=PL...
fetchit --best --last 10 https://youtube.com/playlist?list=PL...

The --last flag selects the final N videos by playlist order, not by upload date. If the playlist is sorted chronologically (newest first), --last 5 grabs the most recent 5 entries. Combined with --reverse, you can control which end of the playlist is targeted.

Reverse order

By default, videos download in playlist order (first to last). Pass --reverse to download from last to first.

CLI
fetchit --best --reverse https://youtube.com/playlist?list=PL...
fetchit --best --items 1-10 --reverse https://youtube.com/playlist?list=PL...

This is useful when you want the final video in a playlist to finish first — for example, if you are watching in release order but want to save the finale for last.

Combined with other flags

All scriptable-mode flags work with --items, --reverse, and --last:

CLI
fetchit --mp3 --items 1-20 https://youtube.com/playlist?list=PL...
fetchit --chapters --last 3 https://youtube.com/playlist?list=PL...
fetchit --from 5:30 --to 10:15 --items 3,7 https://youtube.com/playlist?list=PL...

When combining --from/--to time ranges with a playlist, the time range is applied to every selected video. Each video is clipped to the same start and end times.

Output directory structure

Playlist downloads use a different output layout than single-video downloads. Instead of saving individual files directly to the output directory, fetchit groups them into a subfolder named after the playlist.

Default structure

BASH
~/Downloads/
  My Cool Playlist/
    01 - First Video.mp4
    02 - Second Video.mp4
    03 - Third Video.mp4
    ...

Playlist folder naming convention

The folder name is derived from the playlist title returned by yt-dlp, sanitised to remove characters that are invalid on your filesystem:

  • Characters \ / : * ? " < > | are replaced with underscores or removed
  • Leading and trailing whitespace is trimmed
  • If the title is empty or contains only invalid characters, the playlist ID is used as a fallback
  • Truncated to 200 characters to avoid ENAMETOOLONG errors on Windows

File naming within playlists

Individual files follow a numbered prefix convention to preserve playlist ordering:

JSON
{index:02d} - {title} [{id}].{ext}

The {index:02d} portion is the video's position in the playlist, zero-padded to at least 2 digits. This ensures alphabetical sorting matches playlist order. For playlists with 100+ items, the padding expands to 3 digits (001).

Playlist sizeIndex formatExample
1-99 items{index:02d}01 - ...
100-999 items{index:03d}042 - ...
1000+ items{index:04d}1003 - ...

Custom output directory

Override the parent directory with the -o flag. The playlist subfolder is still created inside the specified path:

CLI
fetchit --best -o ~/Videos/Playlists https://youtube.com/playlist?list=PL...

Produces:

BASH
~/Videos/Playlists/My Cool Playlist/
  01 - First Video.mp4
  02 - Second Video.mp4

Skip the playlist folder

If you prefer all files to land flat in a single directory without playlist grouping, use the --flat flag:

CLI
fetchit --best --flat https://youtube.com/playlist?list=PL...

Files are named with the playlist title and index prefix directly:

BASH
~/Downloads/My Cool Playlist - 01 - First Video.mp4
~/Downloads/My Cool Playlist - 02 - Second Video.mp4

Custom output templates

For full control over file naming, use the --output-template flag. This accepts yt-dlp-style output template variables.

Available template variables

VariableDescriptionExample value
%(playlist_title)sTitle of the playlistMy Cool Playlist
%(playlist_id)sPlaylist IDPL12345ABCDE
%(playlist_index)sIndex within the playlist3
%(playlist_autonumber)sAuto-incrementing number across all playlists5
%(title)sVideo titleFirst Video
%(id)sVideo IDabc123def45
%(uploader)sChannel or creator nameChannel Name
%(duration)sDuration in seconds245
%(ext)sFile extensionmp4
%(resolution)sVideo resolution1920x1080

Template examples

BASH
# Default template
fetchit --best --output-template "%(playlist_index)02d - %(title)s [%(id)s].%(ext)s" https://...

# Include uploader
fetchit --best --output-template "%(uploader)s - %(title)s.%(ext)s" https://...

# Full path template
fetchit --best --output-template "%(playlist_title)s/%(playlist_index)02d - %(title)s.%(ext)s" https://...

# Custom folder with channel
fetchit --best --output-template "YouTube/%(uploader)s/%(playlist_title)s/%(title)s.%(ext)s" https://...

When using a template that includes %(playlist_title)s in a path component, the same sanitisation rules apply as for the default folder naming. If the template omits %(playlist_index)s, files are still named with the index prefix to preserve order.

Concurrency and parallel downloads

fetchit downloads playlist items concurrently to maximise throughput. By default, up to 3 videos download simultaneously.

Why parallel?

Sequential downloading (one video at a time) underutilises your network connection, especially for short videos where the overhead of probing and negotiation dominates. Parallel downloads keep the pipeline full and reduce total batch time significantly.

Default behaviour

The default concurrency is 3 concurrent downloads. This strikes a balance between speed and reliability on most consumer internet connections. Each download runs in its own yt-dlp process with independent progress tracking.

Tuning concurrency

CLI
fetchit --best --concurrency 5 https://youtube.com/playlist?list=PL...
fetchit --best --concurrency 1 https://youtube.com/playlist?list=PL...   # sequential
ConcurrencyUse case
1Sequential — minimum bandwidth usage, polite to the server
3Default — balanced throughput for typical home connections
5Aggressive — fast on high-bandwidth connections (>100 Mbps)
10+Maximum speed — only if you have a very fast connection and the server allows it

YouTube throttling

YouTube intentionally throttles parallel connections to the same stream. When you download multiple videos from the same YouTube playlist simultaneously, each video comes from a different CDN edge server, so the throttling is per-stream rather than global. However, YouTube may still rate-limit your IP if you open too many concurrent connections.

In practice, concurrency values above 5 rarely improve total download time on YouTube. If you see individual download speeds dropping as concurrency increases, you have hit YouTube's per-IP limit. Reduce --concurrency or use a VPN to distribute across different IPs.

For non-YouTube sources (Threads, Instagram, direct video hosts), higher concurrency values are often more effective because these platforms do not enforce the same per-IP limits. Experiment with --concurrency 8 or higher for these sources.

Monitoring concurrent downloads

In interactive mode, fetchit shows separate progress bars for each active download, stacked vertically. Each bar includes the video title, percentage, speed, and ETA. Completed bars collapse into a summary line. In scriptable mode, the output is line-based with each download completing on its own line.

Metadata embedding in batch

When downloading playlists, fetchit embeds additional metadata into each file to help media organisers identify the content.

What gets embedded

Metadata fieldSourceExample
Playlist titleyt-dlp playlist metadataMy Cool Playlist
Track numberPlaylist index3/20
Track totalTotal playlist size20
Video titlePer-video metadataFirst Video
UploaderChannel / creator nameChannel Name
Upload dateVideo publish date2025-12-01
DescriptionVideo description (truncated)In this video we...

This metadata is written as standard MP4/MKV tags, which media servers like Plex, Jellyfin, and Emby can read. For audio files, iTunes-style metadata tags are used so playlists appear correctly in music library applications.

Enabling chapter embedding

Add the --chapters flag to embed chapter markers in every downloaded video:

CLI
fetchit --best --chapters https://youtube.com/playlist?list=PL...

Each video's chapters are embedded independently. This is useful for lecture playlists, podcast episodes, or any content with internal section markers.

Combining playlists with other flags

All of fetchit's single-video flags work with playlist downloads. Here are the most useful combinations:

Audio extraction

BASH
# Download entire playlist as MP3
fetchit --mp3 https://youtube.com/playlist?list=PL...

# Download first 10 as MP3
fetchit --mp3 --items 1-10 https://youtube.com/playlist?list=PL...

# Download last 5 as audio with chapters
fetchit --mp3 --chapters --last 5 https://youtube.com/playlist?list=PL...

Best quality batch

CLI
fetchit --best https://youtube.com/playlist?list=PL...
fetchit --best --concurrency 5 https://youtube.com/playlist?list=PL...
fetchit --best --reverse https://youtube.com/playlist?list=PL...

Time range clipping across a playlist

BASH
# Clip first 2 minutes of every video in the playlist
fetchit --to 2:00 https://youtube.com/playlist?list=PL...

# Clip specific section from each of the first 3 videos
fetchit --from 1:00 --to 3:30 --items 1-3 https://youtube.com/playlist?list=PL...

When using time ranges with playlists, the range is applied uniformly. You cannot specify different ranges for different items in a single command.

Chapters in batch

CLI
fetchit --best --chapters https://youtube.com/playlist?list=PL...
fetchit --mp3 --chapters --items 5-15 https://youtube.com/playlist?list=PL...
Flags like --best and --mp3 are mutually exclusive. You cannot combine them in a single command. If you need some videos in MP3 and others as video, run two separate commands with --items targeting different indices.

Supported playlist sources

fetchit inherits playlist support from yt-dlp, which recognises playlists on hundreds of sites. Here are the most commonly used sources:

YouTube

Full support for public playlists, unlisted playlists (if you have the link), channel upload feeds, mixes, and music playlists. Private playlists require passing browser cookies via --cookies-from-browser. YouTube rate-limits heavy playlist downloads — see the limitations section below.

Threads threads

Threads posts that contain multiple images or videos are treated as a playlist. Each media item is a separate entry. This is useful for saving entire photo dumps or multi-video threads at once.

Instagram carousels

Instagram posts with multiple images or videos (carousels) are detected as playlists. Each carousel item is a separate entry. This works for both feed posts and story highlights.

Other supported sources

SourcePlaylist typeNotes
BilibiliSeries / collectionEpisode series and user-created collections
SoundCloudSets / playlistsAudio playlists, albums, and user sets
TwitchCollectionsCurated collections of VODs
VimeoAlbums / showcasesCurated video albums and showcases
DailymotionPlaylistsUser-created playlists and channel feeds
FacebookWatch playlistsPublic video playlists from pages

Limitations and known issues

YouTube rate limiting

Downloading large playlists from YouTube triggers rate-limiting after 30-50 videos in a short period. YouTube displays a "Sign in to confirm you're not a bot" page. Mitigations:

  • Use --cookies-from-browser firefox to pass authenticated cookies (Firefox strongly preferred on Windows — Chrome and Edge encrypt cookies)
  • Reduce concurrency to 1 or 2 to appear less aggressive
  • Add a delay between items — fetchit does not yet have a built-in delay flag, but you can wrap it in a shell loop with sleep
  • Use a VPN to distribute requests across different IPs for very large batch downloads
  • If rate-limited, wait 24-48 hours for the flag to reset

Very large playlists

Playlists with more than 200 entries can be slow to probe because yt-dlp fetches metadata for every entry upfront. The probe time scales roughly linearly with the number of entries. For playlists exceeding 500 entries, consider:

  • Using --last N to probe only the most recent N items
  • Breaking the download into multiple commands with --items ranges
  • Monitoring progress via the terminal output

Mixing formats across items

When a selected format is not available for some videos in the batch, fetchit falls back to the best available format for those items. This means you may get inconsistent quality across your downloaded playlist. The fallback is logged but not visually prominent in the TUI.

Memory usage

fetchit keeps all entry metadata in memory during a playlist download. For extremely large playlists (1000+ entries), memory usage can reach 100-200 MB. This is typically not an issue on modern machines but may be noticeable on low-memory systems.

Unicode and special characters

Some playlist and video titles contain emoji, CJK characters, or other Unicode that may not display correctly in all terminals. File names are sanitised for the filesystem, but the interactive checklist displays the raw title as reported by yt-dlp. If you see garbled characters, the source metadata contains encoding that your terminal does not support.

No progress for individual items in scriptable mode

In scriptable mode (--best, --mp3, etc.), fetchit outputs one line per completed video rather than showing real-time progress bars. The output includes the file path and file size after each item finishes. If you need per-video progress visibility, use interactive mode.

Real-world examples

Download a music album playlist as MP3

CLI
fetchit --mp3 --concurrency 3 --chapters \
  https://music.youtube.com/playlist?list=OLAK5uy_...

This downloads an entire YouTube Music album, converts each track to MP3, embeds chapter markers, and saves them to ~/Downloads/{Album Title}/.

Download specific lectures from a course playlist

CLI
fetchit --best --items 3,7,12-15 --concurrency 2 \
  https://youtube.com/playlist?list=PL...

Selects only lectures 3, 7, and 12 through 15 from a large course playlist, downloading them at best quality with 2 concurrent streams.

Save a Threads photo dump

CLI
fetchit --best --flat --output-template "%(playlist_index)02d - %(title)s.%(ext)s" \
  https://www.threads.net/@username/post/...

Downloads all images and videos from a multi-media Threads post into a flat directory with numbered filenames.

Download the latest podcast episodes

CLI
fetchit --mp3 --last 5 --chapters --concurrency 1 \
  https://youtube.com/playlist?list=PL...

Grabs the 5 most recent episodes from a podcast playlist, extracting audio with chapters and downloading sequentially to avoid rate limits.

Convert an entire playlist to audio with custom output

CLI
fetchit --mp3 --output-template "%(uploader)s/%(playlist_title)s/%(playlist_index)02d - %(title)s.%(ext)s" \
  -o "D:/Music" \
  https://youtube.com/playlist?list=PL...

Produces:

BASH
D:/Music/Channel Name/My Playlist/01 - First Track.mp3
D:/Music/Channel Name/My Playlist/02 - Second Track.mp3

Download in reverse order for chronological viewing

CLI
fetchit --best --reverse --concurrency 1 \
  https://youtube.com/playlist?list=PL...

Downloads the playlist from last to first, one at a time. Useful when a playlist is sorted newest-first but you want to watch in chronological (oldest-first) order and download the file you will watch next.

Quick check for how many videos are in a playlist

Use the --dry-run flag to see what would be downloaded without actually downloading anything:

CLI
fetchit --best --dry-run https://youtube.com/playlist?list=PL...
fetchit --best --items 1-5 --dry-run https://youtube.com/playlist?list=PL...

This prints the playlist title, total entry count, and a list of all video titles and indices that would be downloaded. No files are written.

See also

Was this page helpful?