Last active
November 3, 2019 14:41
-
-
Save NicoVIII/0782d813b0a6df276016913baf6fc347 to your computer and use it in GitHub Desktop.
Southpark Downloader (with german and english audio) - Uses youtube-dl and ffmpeg
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/bash | |
# | |
# ARG_POSITIONAL_SINGLE([season],[Season],[]) | |
# ARG_POSITIONAL_SINGLE([episode],[Episode],[]) | |
# ARG_OPTIONAL_BOOLEAN([keep],[k],[Prevents program to delete temporary files]) | |
# ARG_HELP([The general script's help msg]) | |
# ARGBASH_GO() | |
# needed because of Argbash --> m4_ignore([ | |
### START OF CODE GENERATED BY Argbash v2.8.1 one line above ### | |
# Argbash is a bash code generator used to get arguments parsing right. | |
# Argbash is FREE SOFTWARE, see https://argbash.io for more info | |
# Generated online by https://argbash.io/generate | |
die() | |
{ | |
local _ret=$2 | |
test -n "$_ret" || _ret=1 | |
test "$_PRINT_HELP" = yes && print_help >&2 | |
echo "$1" >&2 | |
exit ${_ret} | |
} | |
begins_with_short_option() | |
{ | |
local first_option all_short_options='kh' | |
first_option="${1:0:1}" | |
test "$all_short_options" = "${all_short_options/$first_option/}" && return 1 || return 0 | |
} | |
# THE DEFAULTS INITIALIZATION - POSITIONALS | |
_positionals=() | |
# THE DEFAULTS INITIALIZATION - OPTIONALS | |
_arg_keep="off" | |
print_help() | |
{ | |
printf '%s\n' "The general script's help msg" | |
printf 'Usage: %s [-k|--(no-)keep] [-h|--help] <season> <episode>\n' "$0" | |
printf '\t%s\n' "<season>: Season" | |
printf '\t%s\n' "<episode>: Episode" | |
printf '\t%s\n' "-k, --keep, --no-keep: Prevents program to delete temporary files (off by default)" | |
printf '\t%s\n' "-h, --help: Prints help" | |
} | |
parse_commandline() | |
{ | |
_positionals_count=0 | |
while test $# -gt 0 | |
do | |
_key="$1" | |
case "$_key" in | |
-k|--no-keep|--keep) | |
_arg_keep="on" | |
test "${1:0:5}" = "--no-" && _arg_keep="off" | |
;; | |
-k*) | |
_arg_keep="on" | |
_next="${_key##-k}" | |
if test -n "$_next" -a "$_next" != "$_key" | |
then | |
{ begins_with_short_option "$_next" && shift && set -- "-k" "-${_next}" "$@"; } || die "The short option '$_key' can't be decomposed to ${_key:0:2} and -${_key:2}, because ${_key:0:2} doesn't accept value and '-${_key:2:1}' doesn't correspond to a short option." | |
fi | |
;; | |
-h|--help) | |
print_help | |
exit 0 | |
;; | |
-h*) | |
print_help | |
exit 0 | |
;; | |
*) | |
_last_positional="$1" | |
_positionals+=("$_last_positional") | |
_positionals_count=$((_positionals_count + 1)) | |
;; | |
esac | |
shift | |
done | |
} | |
handle_passed_args_count() | |
{ | |
local _required_args_string="'season' and 'episode'" | |
test "${_positionals_count}" -ge 2 || _PRINT_HELP=yes die "FATAL ERROR: Not enough positional arguments - we require exactly 2 (namely: $_required_args_string), but got only ${_positionals_count}." 1 | |
test "${_positionals_count}" -le 2 || _PRINT_HELP=yes die "FATAL ERROR: There were spurious positional arguments --- we expect exactly 2 (namely: $_required_args_string), but got ${_positionals_count} (the last one was: '${_last_positional}')." 1 | |
} | |
assign_positional_args() | |
{ | |
local _positional_name _shift_for=$1 | |
_positional_names="_arg_season _arg_episode " | |
shift "$_shift_for" | |
for _positional_name in ${_positional_names} | |
do | |
test $# -gt 0 || break | |
eval "$_positional_name=\${1}" || die "Error during argument parsing, possibly an Argbash bug." 1 | |
shift | |
done | |
} | |
parse_commandline "$@" | |
handle_passed_args_count | |
assign_positional_args 1 "${_positionals[@]}" | |
# OTHER STUFF GENERATED BY Argbash | |
### END OF CODE GENERATED BY Argbash (sortof) ### ]) | |
# [ <-- needed because of Argbash | |
# Give season and episode with two digits | |
season=$(printf "%02d" "$_arg_season") | |
episode=$(printf "%02d" "$_arg_episode") | |
seasonName="Season $season" | |
episodeName="Episode ${episode}" | |
folder="$seasonName/$episodeName" | |
mkdir -p "$folder" | |
( | |
cd "$folder" | |
episodeFile="$episodeName.mp4" | |
trackFile="Episode ${episode}_english.m4a" | |
printf "Download video and german audio..." | |
youtube-dl -q --restrict-filenames "http://www.southpark.de/alle-episoden/s${season}e${episode}" | |
ffmpeg -hide_banner -loglevel error -f concat -safe 0 -i <(find . -type f -name '*.mp4' -printf "file '$PWD/%p'\n" | sort) -c copy "${episodeName}_german.mp4" | |
printf "\rDownloaded video and german audio. \n" | |
printf "Download english audio..." | |
youtube-dl -q --restrict-filenames -k -x --geo-bypass "http://southpark.cc.com/full-episodes/s${season}e${episode}" | |
ffmpeg -hide_banner -loglevel error -f concat -safe 0 -i <(find . -type f -name '*.m4a' -printf "file '$PWD/%p'\n" | sort) -c copy "$trackFile" | |
printf "\rDownloaded english audio. \n" | |
# Add english audio to video | |
ffmpeg -hide_banner -loglevel error -i "${episodeName}_german.mp4" -i "$trackFile" -codec copy -map 0:v:0 -map 0:a:0 -map 1:0 -shortest "../$episodeFile" | |
# Normalize | |
#printf "Normalize audio..." | |
#ffmpeg-normalize "$episodeFile" -o "../$episodeFile" -c:a copy | |
#printf "\rNormalized audio. \n" | |
) | |
# Remove subfolder | |
if [ "$_arg_keep" = "off" ]; then | |
( | |
cd "$seasonName" | |
rm -r "$episodeName" | |
) | |
fi | |
# ] <-- needed because of Argbash |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment