Так сложилось, что в данный момент мой рабочий ноутбук оснащен лишь 2GB оперативной памяти. В связи с этим возникла необходимость оптимизации браузера, т.к. при большом количестве открытых вкладок памяти становится недостаточно и используется swap-раздел, что ведет к тормозам.
В процессе работы мне помогает музыка, обычно это открытый таб с плейлистом Youtube. Так вот этот таб в просессе работы съедает до 500MB (!) и даже выше (Google Chrome).
Такое положение дел вынудило написать bash-скрипт, который на входе получает ID плейлиста, на выходе – mp3 файлы, которые можно слушать в любимом плеере, например, в MOC:
Скачать mp3 с Youtube нельзя, поэтому процесс делим на 3 шага:
- скачиваем flv
- извлекаем звуковую дорожку
- удаляем временный flv
На всякий случай напомню, что ID плейлиста это get-параметр «list».
Зависимости:
sudo apt-get install youtube-dl ffmpeg libavcodec-extra-53
- youtube-dl для скачивания видеофайла
- ffmpeg libavcodec-extra-53 для конвертации в mp3
Собственно сам скрипт, подробно прокомментированный(скачать):
#!/bin/bash
usage='usage:
./get_youtube_playlist <playlist_id> <target_folder> <num_songs>
target_folder: (default: songs will be downloaded in current folder)
num_songs: number of songs to get (default: 50)
examples:
./get_youtube_playlist RD02HIkZaLeuF9k
./get_youtube_playlist RD02HIkZaLeuF9k "instrumental hip-hop beats" 10
'
playlist_id=$1
target_folder=$2
num_songs=$3
if [ -z "$playlist_id" ]; then
echo "$usage"
exit 1
fi
if ! [[ "$num_songs" =~ ^[0-9]+$ ]] ; then
num_songs=50
fi
if [ -z "$target_folder" ]; then
target_folder='./'
elif [ ! -d "$target_folder" ]; then
echo "Parameter target_folder is incorrect, $usage"
exit 1
fi
# используем Youtube API для получения списка песен
# https://developers.google.com/youtube/2.0/developers_guide_protocol_playlist_search
youtube_api="`wget -qO- https://gdata.youtube.com/feeds/api/playlists/$(echo $playlist_id)?max-results=$(echo $num_songs)`"
if [ -z "$youtube_api" ]; then
echo "Playlist ID is incorrect, $usage"
exit 1
fi
# cписок ID песен помещаем в массив songs
songs=(
$(echo $youtube_api |
grep -P -o "<media:player url='.*?&" |
grep -P -o "(w|-){11}")
)
if [ -z "$songs" ]; then
echo "Nothing to do, $usage"
exit 1
fi
# теперь работаем с каждой отдельной песней,
# напрямую скачать mp3 нельзя, поэтому имеем 3 шага:
# 1. скачиваем flv
# 2. извлекаем звук в mp3
# 3. удаляем временный flv
for (( i = 1 ; i <= ${#songs[@]} ; i++ ))
do
youtube_id=${songs[$i-1]}
track_number=`printf "%0*d" 2 $i`;
# 1. скачиваем flv
youtube-dl --audio-format=mp3 -o "$(echo $target_folder)/$(echo $youtube_id).flv"
http://youtu.be/$(echo $youtube_id)
if [ -f "$(echo $target_folder)/$(echo $youtube_id).flv" ]
then
# 2. flv -> mp3
avconv -i "$(echo $target_folder)/$(echo $youtube_id).flv"
-y "$(echo $target_folder)/$(echo $track_number). $(echo $youtube_id).mp3"
-acodec libmp3lame -ac 2 -ab 128k -vn
# 3. удаляем flv
rm "$(echo $target_folder)/$(echo $youtube_id).flv"
fi
done
Надеюсь, этот скрипт полезен не только мне и будет экономить много гигабайт оперативной памяти у читателей.
Автор: limonte