Plex Default-Subtitle Sweep (Linux)
Clear default subtitle flags across a media library with ffmpeg stream-copy remux so files Direct Play instead of forcing a transcode — plus a cron job for new downloads.
bash#!/usr/bin/env bash
# Clear the DEFAULT flag on subtitle streams across a media tree.
# Stream-copy remux only (no re-encode, no quality loss).
# Forced subtitle streams keep their forced flag.
set -euo pipefail
MEDIA_DIR="${1:-/media}"
find "$MEDIA_DIR" -type f -name '*.mkv' -print0 | while IFS= read -r -d '' f; do
# Which subtitle streams are marked default?
defaults=$(ffprobe -v error -select_streams s \
-show_entries stream=index:stream_disposition=default,forced \
-of csv=p=0 "$f" | awk -F, '$2==1 {print $1","$3}')
[ -z "$defaults" ] && continue # nothing defaulted, skip (idempotent)
args=()
while IFS=, read -r idx forced; do
# keep forced foreign-dialogue subs forced, just not defaulted
if [ "$forced" = "1" ]; then
args+=(-disposition:s:"$idx" forced)
else
args+=(-disposition:s:"$idx" 0)
fi
done <<< "$defaults"
tmp="${f%.mkv}.sweep.mkv"
if ffmpeg -v error -fflags +genpts -i "$f" \
-map 0 -map_metadata 0 -map_chapters 0 -c copy \
-max_interleave_delta 0 "${args[@]}" "$tmp"; then
mv -f "$tmp" "$f"
echo "swept: $f"
else
rm -f "$tmp"
echo "FAILED (left untouched): $f" >&2
fi
done
What this does
A subtitle track marked default tells the client to display it, which forces Plex to burn the subtitle into the video — a full transcode. On low-power hardware that transcode stutters or fails outright. This script walks a media tree, finds every MKV with a defaulted subtitle stream, and clears the default flag with an ffmpeg stream-copy remux (no re-encode, so zero quality loss and it runs in seconds per file). Forced foreign-dialogue subtitles keep their forced flag so they still show when needed.
After the sweep, files Direct Play and the subtitles are still there — just off by default, ready to toggle on manually.
Prerequisites
ffmpegandffprobeinstalled (sudo apt-get install -y ffmpeg)- Read/write access to the media folder
- Run against a backup or a copy first if you’re nervous — the remux is lossless but it does overwrite in place
Usage
Point it at your media root (defaults to /media):
chmod +x sub-sweep.sh
./sub-sweep.sh /media/Movies
Auto-sweep new downloads with cron
To keep new downloads clean, run a lightweight version every 30 minutes that only touches recently-modified files:
# Only scan MKVs modified in the last 90 minutes, then sweep them.
# Add to root's crontab: crontab -e
*/30 * * * * find /media -name '*.mkv' -mmin -90 -print0 | \
xargs -0 -I{} /usr/local/bin/sub-sweep-one.sh "{}" >> /var/log/sub-sweep.log 2>&1
Notes
- Timestamp errors: some MKVs fail with “Can’t write packet with unknown timestamp.” The
-fflags +genpts -max_interleave_delta 0flags in the script fix that — keep them. - Idempotent: a file with no defaulted subtitle is skipped, so re-running is safe and cheap.
- MKV only: the script targets
.mkv. MP4 rarely carries the problematic image subtitle formats, but you can add-o -name '*.mp4'to thefindif needed. - Not
mkvpropedit?mkvpropeditcan flip the flag without a remux and is faster if installed, butffmpegis far more commonly available (it ships on most NAS boxes), so this script uses it.