Filter '|' characters out of video titles.
This commit is contained in:
parent
1d2872731a
commit
1fff38e4e6
161
README.txt
161
README.txt
|
@ -1,50 +1,153 @@
|
||||||
===============================================================================
|
===============================================================================
|
||||||
SHELLTUBE Shell scripts for easy YT-browsing
|
SHELLTUBE Browse YT with a hood on
|
||||||
===============================================================================
|
===============================================================================
|
||||||
shelltube will be a collection of (pretty POSIX) shell scripts to
|
shelltube is a simples shell-script that lets you browse Youtube--
|
||||||
browse YouTube quickly, and entirely without captive UIs.
|
searching for playlists, videos, channels, showing their metadata
|
||||||
Right now, there's only one script, yt-search
|
(including items on playlsits and channels, etc) all from the terminal.
|
||||||
|
|
||||||
shelltube is written in pure shell; its only dependencies
|
It YouTube quickly, and entirely without a captive UI.
|
||||||
are any modern shell (pdksh, bash, zsh), lynx, and curl/wget/ftp.
|
|
||||||
Your terminal should accept ANSI color-codes, too~
|
|
||||||
|
|
||||||
Before, shelltube was a set of scripts that culimated in a wrapper
|
shelltube is written in pure shell; its only dependencies are any
|
||||||
script for browsing Youtube (like mpsyt). You could even download
|
modern shell (pdksh, bash, zsh), lynx, and curl/wget/ftp.
|
||||||
videos from YT in pure shell! But, now, all videos require JS execution
|
|
||||||
to download (as far as I can tell), so it stopped working.
|
|
||||||
|
|
||||||
Now I'm refocusing a bit, ditching the wrapper script (begone, captive UIs,
|
Your terminal should accept ANSI color-codes, and be >79chars wide,
|
||||||
ye spectre of ole!), and starting from scratch. :)
|
for best experience~
|
||||||
|
|
||||||
|
shelltube isn't for downloading videos-- it's for *browsing* for them.
|
||||||
|
Use youtube-dl or something for that, that's not my job. :P
|
||||||
|
|
||||||
|
|
||||||
|
----------------------------------------
|
||||||
|
INSTALLATION
|
||||||
|
----------------------------------------
|
||||||
|
Just place "ytlib.sh" in either the CWD, ./lib/ytlib.sh, /usr/lib/, or
|
||||||
|
/usr/local/lib/
|
||||||
|
|
||||||
|
Then put `gendl` and `yt` in your $PATH. /usr/local/bin/ is nice (IMO),
|
||||||
|
or ~/bin/.
|
||||||
|
|
||||||
|
Profit!
|
||||||
|
|
||||||
|
|
||||||
|
----------------------------------------
|
||||||
|
EXAMPLES
|
||||||
|
----------------------------------------
|
||||||
|
yt video --search "wixoss op 1"
|
||||||
|
yt v -s "wixoss op 1"
|
||||||
|
|
||||||
|
yt playlist --search "my hero academia ops"
|
||||||
|
yt p -s "my hero academia ops"
|
||||||
|
|
||||||
|
yt playlist --title "PLY4D6ucZdLWC_yM3R_A1Hj9fAXZO_rSeK"
|
||||||
|
yt p -t "PLY4D6ucZdLWC_yM3R_A1Hj9fAXZO_rSeK"
|
||||||
|
|
||||||
|
yt playlist --list "PLY4D6ucZdLWC_yM3R_A1Hj9fAXZO_rSeK"
|
||||||
|
yt p -l "PLY4D6ucZdLWC_yM3R_A1Hj9fAXZO_rSeK"
|
||||||
|
|
||||||
|
yt video --author "https://youtube.com/watch?v=yu0HjPzFYnY"
|
||||||
|
yt v -a "https://youtube.com/watch?v=yu0HjPzFYnY"
|
||||||
|
|
||||||
|
yt video --desc "https://youtube.com/watch?v=yu0HjPzFYnY"
|
||||||
|
yt v -d "https://youtube.com/watch?v=yu0HjPzFYnY"
|
||||||
|
|
||||||
|
yt video --date "https://youtube.com/watch?v=yu0HjPzFYnY"
|
||||||
|
yt v -D "https://youtube.com/watch?v=yu0HjPzFYnY"
|
||||||
|
|
||||||
|
|
||||||
----------------------------------------
|
----------------------------------------
|
||||||
USAGE
|
USAGE
|
||||||
----------------------------------------
|
----------------------------------------
|
||||||
|
|
||||||
YT-SEARCH
|
YT
|
||||||
--------------------
|
--------------------
|
||||||
yt-search lists videos matching a certain search query.
|
`yt` is the shelltube script-- it's executed with a subcommand [arguments]
|
||||||
USAGE: yt-search [-csmb] query
|
system, like `apt` or `git`.
|
||||||
|
|
||||||
Each option [-csmb] represents a different format-method.
|
USAGE: yt subcommand action [arguments]
|
||||||
-b big TITLE \n DURATION | VIEWS | URL
|
|
||||||
-m medium TITLE | DURATION | URL
|
|
||||||
-s small TITLE | URL
|
|
||||||
-c compact TITLE | ID
|
|
||||||
|
|
||||||
Big takes up two lines, while the rest only use one.
|
The subcommands are:
|
||||||
If you're piping output, you might wanna usa -m, -s, or -c.
|
* (v)ideo
|
||||||
|
* (p)laylist
|
||||||
|
|
||||||
|
They refer to actions related to videos and playlists, respectively.
|
||||||
|
|
||||||
|
Every subcommand and action thereof supports "-h" and "--help".
|
||||||
|
|
||||||
|
|
||||||
YT-DESC
|
|
||||||
|
YT VIDEO
|
||||||
--------------------
|
--------------------
|
||||||
yt-desc prints the description of a YT video.
|
`yt video` is for anything related to videos-- here it is:
|
||||||
USAGE: yt-desc url/id
|
|
||||||
|
|
||||||
The only argument it takes is the URL/ID of the video.
|
USAGE: yt (v)ideo [action]
|
||||||
This script requires `lynx`.
|
|
||||||
|
Here are the actions:
|
||||||
|
|
||||||
|
SHORT LONG ARGUMENTS
|
||||||
|
----------------------------------------------
|
||||||
|
-s --search [-csmb] search_query
|
||||||
|
-t --title url/id
|
||||||
|
-d --desc url/id
|
||||||
|
-v --views url/id
|
||||||
|
-a --author [-nu] url/id
|
||||||
|
-D --date url/id
|
||||||
|
|
||||||
|
The only actions with weird arguments are --search and --author:
|
||||||
|
* normally, --author returns the channel URL and name on two
|
||||||
|
seperate lines
|
||||||
|
* "--author -n" returns only the name
|
||||||
|
* "--author -u" returns only the URL
|
||||||
|
|
||||||
|
* normally, --search prints results in the "big" format (title on
|
||||||
|
one line, other metadata on second line)
|
||||||
|
* "--search -c" for "compact" format, etc.
|
||||||
|
* "-c", "-s", "-m", "-b", for "compact", "small", "medium", and "big",
|
||||||
|
respectively
|
||||||
|
|
||||||
|
|
||||||
|
YT PLAYLIST
|
||||||
|
--------------------
|
||||||
|
`yt playlist` is for anything related to playlists-- here it is:
|
||||||
|
|
||||||
|
USAGE: yt (p)laylist [action]
|
||||||
|
|
||||||
|
Here are the actions:
|
||||||
|
|
||||||
|
SHORT LONG ARGUMENTS
|
||||||
|
----------------------------------------------
|
||||||
|
-s --search [-csmb] search_query
|
||||||
|
-l --list [-csmb] url/id
|
||||||
|
-t --title url/id
|
||||||
|
-v --views url/id
|
||||||
|
-a --author [-nu] url/id
|
||||||
|
-D --date url/id
|
||||||
|
|
||||||
|
The only actions with weird arguments are --search, --list and --author:
|
||||||
|
* --author acts just like "video --author"
|
||||||
|
* --search acts just like "video --search"
|
||||||
|
* --list acts just like --search, with [-csmb]
|
||||||
|
|
||||||
|
|
||||||
|
YT CHANNEL
|
||||||
|
--------------------
|
||||||
|
`yt channel` is for anything related to channels-- here it is:
|
||||||
|
|
||||||
|
USAGE: yt (c)hannel [action]
|
||||||
|
|
||||||
|
Here are the actions:
|
||||||
|
|
||||||
|
SHORT LONG ARGUMENTS
|
||||||
|
----------------------------------------------
|
||||||
|
-s --search [-csmb] search_query
|
||||||
|
-l --list [-csmb] url/id
|
||||||
|
-t --title url/id
|
||||||
|
-d --desc url/id
|
||||||
|
-v --subscribers url/id
|
||||||
|
-D --date url/id
|
||||||
|
|
||||||
|
The only actions with weird arguments are --search, --list and --author:
|
||||||
|
* --search acts just like "video --search"
|
||||||
|
* --list acts just like "playlist --search"
|
||||||
|
|
||||||
|
|
||||||
GENDL
|
GENDL
|
||||||
|
@ -70,4 +173,4 @@ BORING STUFF
|
||||||
----------------------------------------
|
----------------------------------------
|
||||||
License is in COPYING.txt (GNU GPLv3~! <3)
|
License is in COPYING.txt (GNU GPLv3~! <3)
|
||||||
Author is Jenga Phoenix <jadedctrl@teknik.io>
|
Author is Jenga Phoenix <jadedctrl@teknik.io>
|
||||||
Sauce is at https://git.eunichx.us/shelltube
|
Sauce is at https://git.eunichx.us/shelltube.git
|
||||||
|
|
44
TODO.txt
44
TODO.txt
|
@ -1,44 +0,0 @@
|
||||||
At some point in time, this SHOULD be the readme. It isn't right now, obviously.
|
|
||||||
|
|
||||||
===============================================================================
|
|
||||||
SHELLTUBE Shell scripts for easy YT-browsing
|
|
||||||
===============================================================================
|
|
||||||
shelltube is a collection of (pretty POSIX) shell scripts to
|
|
||||||
browse YouTube quickly, and entirely without captive UIs.
|
|
||||||
|
|
||||||
shellTube is written in pure shell; its only dependencies
|
|
||||||
are any modern shell (pdksh, bash, zsh) and curl/wget/ftp.
|
|
||||||
Your terminal should accept ANSI color-codes, too~
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
----------------------------------------
|
|
||||||
USAGE
|
|
||||||
----------------------------------------
|
|
||||||
There are three different scripts that make up shelltube:
|
|
||||||
* yt-search
|
|
||||||
* yt-channel
|
|
||||||
* yt-meta
|
|
||||||
|
|
||||||
In all three scripts:
|
|
||||||
'index' means what page of results you're on--
|
|
||||||
'results' means how many of them will be displayed.
|
|
||||||
|
|
||||||
yt-search lists videos matching a certain search query.
|
|
||||||
USAGE: yt-search [-i index] [-r results] query
|
|
||||||
|
|
||||||
|
|
||||||
yt-channel lists the videos of a given channel.
|
|
||||||
USAGE: yt-channel [-i index] [-r results] URL/ID/name
|
|
||||||
|
|
||||||
yt-meta lists the metadata of a given video
|
|
||||||
USAGE: yt-meta URL/ID
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
----------------------------------------
|
|
||||||
BORING STUFF
|
|
||||||
----------------------------------------
|
|
||||||
License is in COPYING.txt (GNU GPLv3~! <3)
|
|
||||||
Author is Jenga Phoenix <jadedctrl@teknik.io>
|
|
||||||
Sauce is at https://git.eunichx.us/shelltube
|
|
|
@ -0,0 +1,141 @@
|
||||||
|
#!/bin/sh
|
||||||
|
########################################
|
||||||
|
# name: yt
|
||||||
|
# lisc: gnu gplv3
|
||||||
|
# main: jadedctrl
|
||||||
|
# desc: browse youtube from the terminal
|
||||||
|
########################################
|
||||||
|
|
||||||
|
# ... there's got to be a better way to
|
||||||
|
# source this.
|
||||||
|
if test -e ytlib.sh; then
|
||||||
|
. ./ytlib.sh
|
||||||
|
elif test -e lib/ytlib.sh; then
|
||||||
|
. ./lib/ytlib.sh
|
||||||
|
elif test -e ../lib/ytlib.sh; then
|
||||||
|
. ../lib/ytlib.sh
|
||||||
|
elif test -e /usr/local/lib/ytlib.sh; then
|
||||||
|
. /usr/local/lib/ytlib.sh
|
||||||
|
elif test -e /usr/lib/ytlib.sh; then
|
||||||
|
. /usr/lib/ytlib.sh
|
||||||
|
else
|
||||||
|
echo "ytlib.sh not found."
|
||||||
|
exit 5
|
||||||
|
fi
|
||||||
|
|
||||||
|
# --------------------------------------
|
||||||
|
|
||||||
|
# Show usage message of shelltube itself
|
||||||
|
function yt_usage {
|
||||||
|
echo "usage: yt command subcommand [arguments]"
|
||||||
|
echo " yt (v)ideo [...]"
|
||||||
|
echo " yt (p)laylist [...]"
|
||||||
|
exit 2
|
||||||
|
}
|
||||||
|
|
||||||
|
# --------------------------------------
|
||||||
|
|
||||||
|
if test -z "$1"; then
|
||||||
|
yt_usage
|
||||||
|
fi
|
||||||
|
|
||||||
|
# --------------------------------------
|
||||||
|
|
||||||
|
# Show usage message of the video subcommand
|
||||||
|
function video_usage {
|
||||||
|
echo "usage: yt video --(s)earch [...]"
|
||||||
|
echo " yt video --(t)itle [...]"
|
||||||
|
echo " yt video --(d)esc [...]"
|
||||||
|
echo " yt video --(a)uthor [...]"
|
||||||
|
echo " yt video --(v)iews [...]"
|
||||||
|
echo " yt video --(D)ate [...]"
|
||||||
|
|
||||||
|
exit 2
|
||||||
|
}
|
||||||
|
|
||||||
|
# Pass on commands to video subcommand
|
||||||
|
function video_invocation {
|
||||||
|
local command="$1"
|
||||||
|
local arguments="$(echo "$@" | awk '{$1=""; print}')"
|
||||||
|
|
||||||
|
if test -z "$command"; then
|
||||||
|
video_usage
|
||||||
|
elif test "$(length "$arguments")" -eq 0; then
|
||||||
|
arguments="-h"
|
||||||
|
fi
|
||||||
|
|
||||||
|
case "$command" in
|
||||||
|
"--search") video_search_invocation $arguments;;
|
||||||
|
"-s") video_search_invocation $arguments;;
|
||||||
|
"-d") video_desc_invocation $arguments;;
|
||||||
|
"--desc") video_desc_invocation $arguments;;
|
||||||
|
"-D") video_uploaded_invocation $arguments;;
|
||||||
|
"--date") video_uploaded_invocation $arguments;;
|
||||||
|
"--views") video_views_invocation $arguments;;
|
||||||
|
"-v") video_views_invocation $arguments;;
|
||||||
|
"--author") video_author_invocation $arguments;;
|
||||||
|
"-a") video_author_invocation $arguments;;
|
||||||
|
"--title") video_title_invocation $arguments;;
|
||||||
|
"-t") video_title_invocation $arguments;;
|
||||||
|
"--help") video_usage;;
|
||||||
|
"-h") video_usage;;
|
||||||
|
esac
|
||||||
|
}
|
||||||
|
|
||||||
|
# --------------------------------------
|
||||||
|
|
||||||
|
# Show playlist usage message
|
||||||
|
function playlist_usage {
|
||||||
|
echo "usage: yt playlist --(s)earch [...]"
|
||||||
|
echo " yt playlist --(l)ist [...]"
|
||||||
|
echo " yt playlist --(t)itle [...]"
|
||||||
|
echo " yt playlsit --(a)uthor [...]"
|
||||||
|
echo " yt playlist --(v)iews [...]"
|
||||||
|
echo " yt playlist --(D)ate [...]"
|
||||||
|
exit 2
|
||||||
|
}
|
||||||
|
|
||||||
|
# Pass on commands to the playlist subcommand
|
||||||
|
function playlist_invocation {
|
||||||
|
local command="$1"
|
||||||
|
local arguments="$(echo "$@" | awk '{$1=""; print}')"
|
||||||
|
|
||||||
|
if test -z "$command"; then
|
||||||
|
playlist_usage
|
||||||
|
elif test "$(length "$arguments")" -eq 0; then
|
||||||
|
arguments="-h"
|
||||||
|
fi
|
||||||
|
|
||||||
|
case "$command" in
|
||||||
|
"--search") playlist_search_invocation $arguments;;
|
||||||
|
"-s") playlist_search_invocation $arguments;;
|
||||||
|
"--views") playlist_views_invocation $arguments;;
|
||||||
|
"-v") playlist_views_invocation $arguments;;
|
||||||
|
"--author") playlist_author_invocation $arguments;;
|
||||||
|
"-a") playlist_author_invocation $arguments;;
|
||||||
|
"--date") playlist_uploaded_invocation $arguments;;
|
||||||
|
"-D") playlist_uploaded_invocation $arguments;;
|
||||||
|
"--title") playlist_title_invocation $arguments;;
|
||||||
|
"-t") playlist_title_invocation $arguments;;
|
||||||
|
"--list") playlist_list_invocation $arguments;;
|
||||||
|
"-l") playlist_list_invocation $arguments;;
|
||||||
|
"--help") playlist_usage;;
|
||||||
|
"-h") playlist_usage;;
|
||||||
|
esac
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
# --------------------------------------
|
||||||
|
# actual invocation
|
||||||
|
|
||||||
|
command="$1"
|
||||||
|
arguments="$(echo "$@" | awk '{$1=""; print}')"
|
||||||
|
case "$command" in
|
||||||
|
*video) video_invocation $arguments;;
|
||||||
|
*v) video_invocation $arguments;;
|
||||||
|
*channel) channel_invocation $arguments;;
|
||||||
|
*c) channel_invocation $arguments;;
|
||||||
|
*playlist) playlist_invocation $arguments;;
|
||||||
|
*p) playlist_invocation $arguments;;
|
||||||
|
esac
|
44
yt-desc
44
yt-desc
|
@ -1,44 +0,0 @@
|
||||||
#!/bin/sh
|
|
||||||
##############################
|
|
||||||
# name: yt-desc
|
|
||||||
# lisc: gnu gplv3
|
|
||||||
# main: jadedctrl
|
|
||||||
# desc: print desc of yt video
|
|
||||||
##############################
|
|
||||||
|
|
||||||
# Usage: yt-desc "$url/id"
|
|
||||||
|
|
||||||
# STRING --> STRING
|
|
||||||
# Get the description of a YT video, from HTML.
|
|
||||||
function video_desc {
|
|
||||||
local html="$1"
|
|
||||||
|
|
||||||
echo "$html" \
|
|
||||||
| grep "action-panel-details" \
|
|
||||||
| sed 's/.*<p .*class="" >//' \
|
|
||||||
| sed 's%</p>.*%%' \
|
|
||||||
| lynx -stdin -dump \
|
|
||||||
| sed 's/^ //'
|
|
||||||
}
|
|
||||||
|
|
||||||
# --------------------------------------
|
|
||||||
# invocation
|
|
||||||
|
|
||||||
function usage {
|
|
||||||
echo "usage: yt-desc url/id"
|
|
||||||
exit 2
|
|
||||||
}
|
|
||||||
|
|
||||||
# --------------------------------------
|
|
||||||
|
|
||||||
if test -z "$1"; then
|
|
||||||
usage
|
|
||||||
elif echo "$1" | grep "youtube" > /dev/null; then
|
|
||||||
URL="$1"
|
|
||||||
else
|
|
||||||
URL="https://www.youtube.com/watch?v=${1}"
|
|
||||||
fi
|
|
||||||
|
|
||||||
# --------------------------------------
|
|
||||||
|
|
||||||
video_desc "$(gendl "$URL")"
|
|
250
yt-search
250
yt-search
|
@ -1,250 +0,0 @@
|
||||||
#!/bin/sh
|
|
||||||
##############################
|
|
||||||
# name: yt-search
|
|
||||||
# lisc: gnu gplv3
|
|
||||||
# main: jadedctrl
|
|
||||||
# desc: search youtube simply.
|
|
||||||
##############################
|
|
||||||
|
|
||||||
# Usage: yt-search [-csmb] "$search_string"
|
|
||||||
|
|
||||||
# --------------------------------------
|
|
||||||
# a bit of math...
|
|
||||||
|
|
||||||
# NUMBER NUMBER --> NUMBER
|
|
||||||
# Well, subtraction. Y'know...
|
|
||||||
function subtract {
|
|
||||||
local operated=$1
|
|
||||||
local operatee=$2
|
|
||||||
echo "${1}-${2}" | bc
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
# --------------------------------------
|
|
||||||
# ... now some string manip...
|
|
||||||
|
|
||||||
# NIL --> STRING
|
|
||||||
# Print an ANSI "unbold" escape string.
|
|
||||||
function unbold {
|
|
||||||
printf "$(tput sgr0)"
|
|
||||||
}
|
|
||||||
|
|
||||||
# STRING --> STRING
|
|
||||||
# Print an ANSI "bold" escape string.
|
|
||||||
function bold {
|
|
||||||
printf "$(tput bold)"
|
|
||||||
}
|
|
||||||
|
|
||||||
# STRING --> NUMBER
|
|
||||||
# Return the length of a string
|
|
||||||
function char_length {
|
|
||||||
subtract $(echo $1 | wc -c) 1
|
|
||||||
}
|
|
||||||
|
|
||||||
# STRING NUMBER [STRING] --> STRING
|
|
||||||
# pad string $1 out to the minimum length $2 with padding $3 (default: "0")
|
|
||||||
function min_string_length {
|
|
||||||
local string="$1"
|
|
||||||
local length=$2
|
|
||||||
if test -z "$3"; then
|
|
||||||
local padding="0"
|
|
||||||
else
|
|
||||||
local padding="$3"
|
|
||||||
fi
|
|
||||||
local new="$string"
|
|
||||||
if test $(char_length $1) -eq $2; then
|
|
||||||
echo $1
|
|
||||||
else
|
|
||||||
while test $(char_length $new) -lt $2; do
|
|
||||||
new="${new}${padding}"
|
|
||||||
done
|
|
||||||
echo $new
|
|
||||||
fi
|
|
||||||
}
|
|
||||||
|
|
||||||
# STRING NUMBER --> STRING
|
|
||||||
# get the first $2 characters in string $1
|
|
||||||
function char_get {
|
|
||||||
local number=$2
|
|
||||||
local string="$1"
|
|
||||||
string="$(min_string_length "$string" $number " ")"
|
|
||||||
echo "$string" \
|
|
||||||
| grep -o "^$(min_string_length "." $number ".")"
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
# --------------------------------------
|
|
||||||
# ... now for the real deal~!
|
|
||||||
|
|
||||||
# STRING --> STRING
|
|
||||||
# Pass the raw search HTML, get raw video result-lines
|
|
||||||
function result_lines {
|
|
||||||
local search_html="$1"
|
|
||||||
echo "$search_html" \
|
|
||||||
| grep "<a href=\"\/watch?v=" \
|
|
||||||
| grep -v "<span class=\"yt-thumb-simple\"" \
|
|
||||||
| grep -v "yt-lockup-playlist-item"
|
|
||||||
#| grep -v "<a href=\"/playlist" \
|
|
||||||
}
|
|
||||||
|
|
||||||
# STRING --> STRING
|
|
||||||
# Return the video ID of a result_line.
|
|
||||||
function result_id {
|
|
||||||
local result_line="$1"
|
|
||||||
echo "$result_line" \
|
|
||||||
| sed 's%.*<a href="/watch?v=%%' \
|
|
||||||
| sed 's%".*%%'
|
|
||||||
}
|
|
||||||
|
|
||||||
function result_url {
|
|
||||||
local result_line="$1"
|
|
||||||
local id="$(result_id "$result_line")"
|
|
||||||
echo "https://youtube.com/watch?v=${id}"
|
|
||||||
}
|
|
||||||
|
|
||||||
# STRING --> STRING
|
|
||||||
# Return the title of a result-line.
|
|
||||||
function result_title {
|
|
||||||
local result_line="$1"
|
|
||||||
echo "$result_line" \
|
|
||||||
| sed 's%.*" title="%%' \
|
|
||||||
| sed 's%".*%%'
|
|
||||||
}
|
|
||||||
|
|
||||||
function result_name {
|
|
||||||
local result_line="$1"
|
|
||||||
local title="$(result_title "$result_line")"
|
|
||||||
echo "$(bold)${title}$(unbold)"
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
# STRING --> STRING
|
|
||||||
# Return the duration of a result-line.
|
|
||||||
function result_duration {
|
|
||||||
local result_line="$1"
|
|
||||||
echo "$result_line" \
|
|
||||||
| sed 's%.*> - Duration: %%' \
|
|
||||||
| sed 's%\..*%%'
|
|
||||||
}
|
|
||||||
|
|
||||||
# STRING --> STRING
|
|
||||||
# Return the .yt-lockup-meta-info <ul> of a result-line
|
|
||||||
function result_meta_ul {
|
|
||||||
local result_line="$1"
|
|
||||||
echo "$result_line" \
|
|
||||||
| sed 's%.*<ul class="yt-lockup-meta-info">%%' \
|
|
||||||
| sed 's%</ul>.*%%'
|
|
||||||
}
|
|
||||||
|
|
||||||
# STRING --> STRING
|
|
||||||
# Return the "Uploaded..." string of a result-line
|
|
||||||
function result_uploaded {
|
|
||||||
local result_line="$1"
|
|
||||||
local result_meta_ul="$(result_meta_ul "$result_line")"
|
|
||||||
echo "$result_meta_ul" \
|
|
||||||
| sed 's%<li>%%' \
|
|
||||||
| sed 's% ago</li>.*%%'
|
|
||||||
}
|
|
||||||
|
|
||||||
# STRING --> NUMBER
|
|
||||||
# Return the view-count of a result-line
|
|
||||||
function result_views {
|
|
||||||
local result_line="$1"
|
|
||||||
local result_meta_ul="$(result_meta_ul "$result_line")"
|
|
||||||
echo "$result_meta_ul" \
|
|
||||||
| sed 's%.*<li>%%g' \
|
|
||||||
| sed 's% views</li>.*%%' \
|
|
||||||
| sed 's%,%%g'
|
|
||||||
}
|
|
||||||
|
|
||||||
# STRING --> STRING
|
|
||||||
# Format a result-line into a mediumly-pretty, one-line string~
|
|
||||||
function result_format_compact {
|
|
||||||
local result_line="$1"
|
|
||||||
local title="$(char_get "$(result_name "$result_line")" 40)$(unbold)"
|
|
||||||
local id="$(result_id "$result_line")"
|
|
||||||
|
|
||||||
echo "$name | $id"
|
|
||||||
}
|
|
||||||
|
|
||||||
# STRING --> STRING
|
|
||||||
# Format a result-line into a mediumly-pretty, one-line string~
|
|
||||||
function result_format_small {
|
|
||||||
local result_line="$1"
|
|
||||||
local name="$(char_get "$(result_name "$result_line")" 40)$(unbold)"
|
|
||||||
local url="$(result_url "$result_line")"
|
|
||||||
|
|
||||||
echo "$name | $url"
|
|
||||||
}
|
|
||||||
|
|
||||||
# STRING --> STRING
|
|
||||||
# Format a result-line into a mediumly-pretty, one-line string~
|
|
||||||
function result_format_medium {
|
|
||||||
local result_line="$1"
|
|
||||||
local name="$(char_get "$(result_name "$result_line")" 40)$(unbold)"
|
|
||||||
local duration="$(result_duration "$result_line")"
|
|
||||||
local url="$(result_url "$result_line")"
|
|
||||||
|
|
||||||
echo "$name | $duration | $url"
|
|
||||||
}
|
|
||||||
|
|
||||||
# STRING --> STRING
|
|
||||||
# Format a result-line into a pretty string~
|
|
||||||
function result_format_big {
|
|
||||||
local result_line="$1"
|
|
||||||
local name="$(char_get "$(result_name "$result_line")" 79)$(unbold)"
|
|
||||||
local duration="$(result_duration "$result_line")"
|
|
||||||
local uploaded="$(result_uploaded "$result_line")"
|
|
||||||
local views="$(result_views "$result_line")"
|
|
||||||
local url="$(result_url "$result_line")"
|
|
||||||
|
|
||||||
echo "$name"
|
|
||||||
echo "$duration | $uploaded | $views | $url"
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
# --------------------------------------
|
|
||||||
# invocation <3
|
|
||||||
|
|
||||||
function usage {
|
|
||||||
echo "usage: yt-search [-csmb] query"
|
|
||||||
exit 2
|
|
||||||
}
|
|
||||||
|
|
||||||
# --------------------------------------
|
|
||||||
|
|
||||||
if test -z "$1"; then
|
|
||||||
usage
|
|
||||||
elif test -n "$2"; then
|
|
||||||
QUERY="$2"
|
|
||||||
case "$1" in
|
|
||||||
"-c") FORMAT="compact" ;;
|
|
||||||
"-s") FORMAT="small" ;;
|
|
||||||
"-m") FORMAT="medium" ;;
|
|
||||||
"-b") FORMAT="big" ;;
|
|
||||||
esac
|
|
||||||
else
|
|
||||||
QUERY="$1"
|
|
||||||
FORMAT="big"
|
|
||||||
fi
|
|
||||||
|
|
||||||
# --------------------------------------
|
|
||||||
|
|
||||||
QUERY="$(echo "$QUERY" | sed 's/ /+/g')"
|
|
||||||
search_html="$(gendl "https://youtube.com/results?search_query=$QUERY")"
|
|
||||||
result_lines="$(result_lines "$search_html")"
|
|
||||||
|
|
||||||
IFS='
|
|
||||||
'
|
|
||||||
|
|
||||||
for result in $result_lines; do
|
|
||||||
case "$FORMAT" in
|
|
||||||
"compact") result_format_compact "$result" ;;
|
|
||||||
"small") result_format_small "$result" ;;
|
|
||||||
"medium") result_format_medium "$result" ;;
|
|
||||||
"big") result_format_big "$result" ;;
|
|
||||||
esac
|
|
||||||
done
|
|
|
@ -0,0 +1,869 @@
|
||||||
|
#/bin/sh
|
||||||
|
########################################
|
||||||
|
# name: ytlib.sh
|
||||||
|
# desc: library for shelltube (`yt`)
|
||||||
|
# main: jadedctrl <jadedctrl@teknik.io>
|
||||||
|
# code: git.eunichx.us/shelltube.git
|
||||||
|
########################################
|
||||||
|
|
||||||
|
# --------------------------------------
|
||||||
|
# generic functions
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Return the first 'word' (space-delimiter) of a string.
|
||||||
|
function car {
|
||||||
|
local string="$1"
|
||||||
|
|
||||||
|
echo "$string" \
|
||||||
|
| awk '{print $1}'
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Return all words after the first word of a string.
|
||||||
|
function cdr {
|
||||||
|
local string="$1"
|
||||||
|
|
||||||
|
echo "$string" \
|
||||||
|
| awk '{$1=""; print}' \
|
||||||
|
| sed 's/^ //'
|
||||||
|
}
|
||||||
|
|
||||||
|
# NUMBER NUMBER --> NUMBER
|
||||||
|
# Well, subtraction. Y'know...
|
||||||
|
function subtract {
|
||||||
|
local operated=$1
|
||||||
|
local operatee=$2
|
||||||
|
echo "${1}-${2}" \
|
||||||
|
| bc
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> NUMBER
|
||||||
|
# Count how many words are in a string.
|
||||||
|
function length {
|
||||||
|
local string="$1"
|
||||||
|
|
||||||
|
echo "$string" \
|
||||||
|
| wc -w
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> NUMBER
|
||||||
|
# Count how many lines are in a string.
|
||||||
|
function line_length {
|
||||||
|
local string="$1"
|
||||||
|
|
||||||
|
echo "$string" \
|
||||||
|
| wc -l
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> NUMBER
|
||||||
|
# Return the length of a string in chars.
|
||||||
|
function char_length {
|
||||||
|
local string="$1"
|
||||||
|
|
||||||
|
subtract $(echo "$string" | wc -c) 1
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING NUMBER [STRING] --> STRING
|
||||||
|
# pad string $1 out to the minimum length $2 with padding $3 (default: "0")
|
||||||
|
function min_string_length {
|
||||||
|
local length="$2"
|
||||||
|
local string="$1"
|
||||||
|
|
||||||
|
if test -z "$3"; then
|
||||||
|
local padding="0"
|
||||||
|
else
|
||||||
|
local padding="$3"
|
||||||
|
fi
|
||||||
|
local new="$string"
|
||||||
|
if test "$length" -le "$(char_length "$string")"; then
|
||||||
|
echo "$string"
|
||||||
|
else
|
||||||
|
while test "$(char_length "$new")" -lt "$length"; do
|
||||||
|
new="${new}${padding}"
|
||||||
|
done
|
||||||
|
echo "$new"
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING NUMBER --> STRING
|
||||||
|
# get the first $2 characters in string $1
|
||||||
|
function char_get {
|
||||||
|
local number="$1"
|
||||||
|
local string="$2"
|
||||||
|
|
||||||
|
string="$(min_string_length "$string" $number " ")"
|
||||||
|
echo "$string" \
|
||||||
|
| grep -o "^$(min_string_length "." $number ".")"
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
# --------------------------------------
|
||||||
|
# ansi colors and such
|
||||||
|
|
||||||
|
# NIL --> STRING
|
||||||
|
# Print an ANSI "unbold" escape string.
|
||||||
|
function unbold {
|
||||||
|
printf "$(tput sgr0)"
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Print an ANSI "bold" escape string.
|
||||||
|
function bold {
|
||||||
|
printf "$(tput bold)"
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Format a URL appropriately.
|
||||||
|
function format_url {
|
||||||
|
local url="$1"
|
||||||
|
|
||||||
|
# playlist/playlist video
|
||||||
|
if echo "$url" | grep -q "playlist?"; then
|
||||||
|
echo "$url" \
|
||||||
|
| sed 's%.*list=%%'
|
||||||
|
# video
|
||||||
|
else
|
||||||
|
echo "$url"
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
# --------------------------------------
|
||||||
|
# result parsing
|
||||||
|
# (playlist items, search -items)
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Pass the raw search HTML, get raw video result-lines
|
||||||
|
function result_lines {
|
||||||
|
local search_html="$1"
|
||||||
|
echo "$search_html" \
|
||||||
|
| grep "<a href=\"\/watch?v=" \
|
||||||
|
| grep -v "<span class=\"yt-thumb-simple\"" \
|
||||||
|
| sed 's/|//g'
|
||||||
|
#| grep -v "<a href=\"/playlist" \
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Return the video ID of a result_line.
|
||||||
|
function result_id {
|
||||||
|
local result_line="$1"
|
||||||
|
|
||||||
|
if echo "$result_line" | grep -q "playlist-item"; then
|
||||||
|
echo "$result_line" \
|
||||||
|
| sed 's%.*?list=%%' \
|
||||||
|
| sed 's%".*%%'
|
||||||
|
elif echo "$result_line" | grep -q "data-title"; then
|
||||||
|
echo "$result_line" \
|
||||||
|
| sed 's%.* data-video-id="%%' \
|
||||||
|
| sed 's%"><td class=".*%%' \
|
||||||
|
| sed 's%".*%%'
|
||||||
|
else
|
||||||
|
echo "$result_line" \
|
||||||
|
| sed 's%.*<a href="/watch?v=%%' \
|
||||||
|
| sed 's%".*%%'
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Return the URL of a result-line.
|
||||||
|
function result_url {
|
||||||
|
local result_line="$1"
|
||||||
|
local id="$(result_id "$result_line")"
|
||||||
|
|
||||||
|
# playlist ID
|
||||||
|
if echo "$id" | grep -q "^PL"; then
|
||||||
|
echo "https://youtube.com/playlist?list=${id}"
|
||||||
|
# video ID
|
||||||
|
else # search result
|
||||||
|
echo "https://youtube.com/watch?v=${id}"
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Return the title of a result-line.
|
||||||
|
function result_title {
|
||||||
|
local result_line="$1"
|
||||||
|
|
||||||
|
|
||||||
|
# playlist video
|
||||||
|
if echo "$result_line" | grep -q "data-title"; then
|
||||||
|
echo "$result_line" \
|
||||||
|
| sed 's%.*data-title="%%' \
|
||||||
|
| sed 's%" data-video-id.*%%' \
|
||||||
|
| sed 's%".*%%'
|
||||||
|
# video
|
||||||
|
else
|
||||||
|
echo "$result_line" \
|
||||||
|
| sed 's%.*" title="%%' \
|
||||||
|
| sed 's%".*%%'
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Return the duration of a result-line.
|
||||||
|
function result_duration {
|
||||||
|
local result_line="$1"
|
||||||
|
|
||||||
|
# playlist
|
||||||
|
if echo "$result_line" | grep -q "playlist-item"; then
|
||||||
|
echo "$result_line" \
|
||||||
|
| sed 's%.*View full playlist (%%' \
|
||||||
|
| sed 's% videos.*%%' \
|
||||||
|
| sed 's%$%v%'
|
||||||
|
# playlist video
|
||||||
|
elif echo "$result_line" | grep -q "data-title"; then
|
||||||
|
echo "00:00"
|
||||||
|
# video
|
||||||
|
else
|
||||||
|
echo "$result_line" \
|
||||||
|
| sed 's%.*> - Duration: %%' \
|
||||||
|
| sed 's%\..*%%'
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Return the channel of a result-line.
|
||||||
|
function result_channel {
|
||||||
|
local result_line="$1"
|
||||||
|
|
||||||
|
# playlist
|
||||||
|
if echo "$result_line" | grep -q "playlist-item"; then
|
||||||
|
# playlist with /user/
|
||||||
|
if echo "$result_line" | grep -q "/user/"; then
|
||||||
|
echo "$result_line" \
|
||||||
|
| sed 's%.*/user/%%' \
|
||||||
|
| sed 's%</a>.*%%' \
|
||||||
|
| sed 's%.*>%%'
|
||||||
|
# playlist with /channel/
|
||||||
|
else
|
||||||
|
echo "$result_line" \
|
||||||
|
| sed 's%.*/channel/%%' \
|
||||||
|
| sed 's%</a>.*%%' \
|
||||||
|
| sed 's%.*>%%'
|
||||||
|
fi
|
||||||
|
# playlist video
|
||||||
|
elif echo "$result_line" | grep -q "data-title"; then
|
||||||
|
echo "Someone, bby <3"
|
||||||
|
# video
|
||||||
|
else
|
||||||
|
# video with /channel/
|
||||||
|
if echo "$result_line" | grep -q "/channel/"; then
|
||||||
|
echo "$result_line" \
|
||||||
|
| sed 's%.*href="/channel/%%' \
|
||||||
|
| sed 's%</a>.*%%' \
|
||||||
|
| sed 's%.*" >%%'
|
||||||
|
# video with /user/
|
||||||
|
elif echo "$result_line" | grep -q "/user/"; then
|
||||||
|
echo "$result_line" \
|
||||||
|
| sed 's%.*href="/user/%%' \
|
||||||
|
| sed 's%".*%%'
|
||||||
|
fi
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Return the .yt-lockup-meta-info <ul> of a result-line
|
||||||
|
function result_meta_ul {
|
||||||
|
local result_line="$1"
|
||||||
|
|
||||||
|
echo "$result_line" \
|
||||||
|
| sed 's%.*<ul class="yt-lockup-meta-info">%%' \
|
||||||
|
| sed 's%</ul>.*%%'
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Return the "Uploaded..." string of a result-line
|
||||||
|
function result_uploaded {
|
||||||
|
local result_line="$1"
|
||||||
|
|
||||||
|
local result_meta_ul="$(result_meta_ul "$result_line")"
|
||||||
|
|
||||||
|
# playlist
|
||||||
|
if echo "$result_line" | grep -q "playlist-item"; then
|
||||||
|
echo "Sometime"
|
||||||
|
# playlist video
|
||||||
|
elif echo "$result_line" | grep -q "data-title"; then
|
||||||
|
echo "Sometime"
|
||||||
|
# video
|
||||||
|
else
|
||||||
|
echo "$result_meta_ul" \
|
||||||
|
| sed 's%<li>%%' \
|
||||||
|
| sed 's% ago</li>.*%%'
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> NUMBER
|
||||||
|
# Return the view-count of a result-line
|
||||||
|
function result_views {
|
||||||
|
local result_line="$1"
|
||||||
|
local result_meta_ul="$(result_meta_ul "$result_line")"
|
||||||
|
|
||||||
|
echo "$result_meta_ul" \
|
||||||
|
| sed 's%.*<li>%%g' \
|
||||||
|
| sed 's% views</li>.*%%' \
|
||||||
|
| sed 's%,%%g'
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Return a result's formatted URL
|
||||||
|
function result_formatted_url {
|
||||||
|
local result_line="$1"
|
||||||
|
|
||||||
|
format_url "$(result_url "$result_line")"
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
# --------------------------------------
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Format a result-line into a mediumly-pretty, one-line string~
|
||||||
|
function result_format_compact {
|
||||||
|
local result_line="$1"
|
||||||
|
local title="$(result_title "$result_line")"
|
||||||
|
|
||||||
|
local format_title="$(bold)$(char_get 40 "$title")$(unbold)"
|
||||||
|
local id="$(result_id "$result_line")"
|
||||||
|
|
||||||
|
echo "$format_title | $id"
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Format a result-line into a mediumly-pretty, one-line string~
|
||||||
|
function result_format_small {
|
||||||
|
local result_line="$1"
|
||||||
|
local title="$(result_title "$result_line")"
|
||||||
|
local url="$(result_formatted_url "$result_line")"
|
||||||
|
|
||||||
|
local format_title="$(bold)$(char_get 40 "$title")$(unbold)"
|
||||||
|
|
||||||
|
echo "$format_title | $url"
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Format a result-line into a mediumly-pretty, one-line string~
|
||||||
|
function result_format_medium {
|
||||||
|
local result_line="$1"
|
||||||
|
local title="$(result_title "$result_line")"
|
||||||
|
local duration="$(result_duration "$result_line")"
|
||||||
|
local url="$(result_formatted_url "$result_line")"
|
||||||
|
|
||||||
|
local format_title="$(bold)$(char_get 40 "$title")$(unbold)"
|
||||||
|
local format_duration="$(char_get 5 "$duration")"
|
||||||
|
|
||||||
|
echo "$format_title | $format_duration | $url"
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Format a result-line into a pretty string~
|
||||||
|
function result_format_big {
|
||||||
|
local result_line="$1"
|
||||||
|
local title="$(result_title "$result_line")"
|
||||||
|
local duration="$(result_duration "$result_line")"
|
||||||
|
local uploaded="$(result_uploaded "$result_line")"
|
||||||
|
local channel="$(result_channel "$result_line")"
|
||||||
|
local url="$(result_formatted_url "$result_line")"
|
||||||
|
|
||||||
|
local format_title="$(bold)$(char_get 79 "$title")$(unbold)"
|
||||||
|
local format_duration="$(char_get 7 "$duration")"
|
||||||
|
local format_uploaded="$(char_get 8 "$uploaded")"
|
||||||
|
local format_channel="$(char_get 15 "$channel")"
|
||||||
|
|
||||||
|
echo "$format_title"
|
||||||
|
echo "$format_duration | $format_uploaded | $format_channel | $url"
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
# --------------------------------------
|
||||||
|
# playlsit metadata
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Get the title of a playlist, from HTML.
|
||||||
|
function playlist_title {
|
||||||
|
local html="$1"
|
||||||
|
|
||||||
|
video_title "$html"
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Get the video-count of a playlist, from HTML.
|
||||||
|
function playlist_duration {
|
||||||
|
local html="$1"
|
||||||
|
|
||||||
|
playlist_header_details "$html" \
|
||||||
|
| sed 's%.*</a></li>%%' \
|
||||||
|
| sed 's%</li>.*%%' \
|
||||||
|
| sed 's%<li>%%'
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Get the view-count of a playlist, from HTML.
|
||||||
|
function playlist_views {
|
||||||
|
local html="$1"
|
||||||
|
|
||||||
|
playlist_header_details "$html" \
|
||||||
|
| sed 's%.*</a></li>%%' \
|
||||||
|
| sed 's%</li><li>Last.*%%' \
|
||||||
|
| sed 's%.*</li><li>%%' \
|
||||||
|
| sed 's% views%%' \
|
||||||
|
| sed 's%,%%'
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Get the uploaded date of a playlist, from HTML.
|
||||||
|
function playlist_uploaded {
|
||||||
|
local html="$1"
|
||||||
|
|
||||||
|
playlist_header_details "$html" \
|
||||||
|
| sed 's%.*</a></li>%%' \
|
||||||
|
| sed 's%.*</li><li>%%' \
|
||||||
|
| sed 's%Last updated on %%' \
|
||||||
|
| sed 's%</li>.*%%'
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Get the author name of a playlist, from HTML.
|
||||||
|
function playlist_author_name {
|
||||||
|
local html="$1"
|
||||||
|
|
||||||
|
playlist_header_details "$html" \
|
||||||
|
| sed 's%</li><li>.*%%' \
|
||||||
|
| sed 's%.* >%%' \
|
||||||
|
| sed 's%</.*%%'
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Get the author URL of a playlist, from HTML.
|
||||||
|
function playlist_author_url {
|
||||||
|
local html="$1"
|
||||||
|
|
||||||
|
local author_name="$(playlist_author_name "$html")"
|
||||||
|
|
||||||
|
playlist_header_details "$html" \
|
||||||
|
| sed 's%'"$author_name"'.*%%' \
|
||||||
|
| sed 's%.*href="%%' \
|
||||||
|
| sed 's%".*%%' \
|
||||||
|
| sed 's%^%https://youtube.com%'
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Return the metadata header for playlist HTML
|
||||||
|
function playlist_header_details {
|
||||||
|
local html="$1"
|
||||||
|
|
||||||
|
echo "$html" \
|
||||||
|
| grep "pl-header-details"
|
||||||
|
}
|
||||||
|
|
||||||
|
# --------------------------------------
|
||||||
|
# video metadata
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Get the description of a YT video, from HTML.
|
||||||
|
function video_desc {
|
||||||
|
local html="$1"
|
||||||
|
|
||||||
|
echo "$html" \
|
||||||
|
| grep "action-panel-details" \
|
||||||
|
| sed 's/.*<p .*class="" >//' \
|
||||||
|
| sed 's%</p>.*%%' \
|
||||||
|
| lynx -stdin -dump \
|
||||||
|
| sed 's/^ //'
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Get the views of a YT video, from HTML.
|
||||||
|
function video_views {
|
||||||
|
local html="$1"
|
||||||
|
|
||||||
|
echo "$html" \
|
||||||
|
| grep "watch-view-count" \
|
||||||
|
| sed 's/.*"watch-view-count">//' \
|
||||||
|
| sed 's/ views.*//' \
|
||||||
|
| sed 's/,//g'
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Get the uploader's name of a YT video, from HTML.
|
||||||
|
function video_author_name {
|
||||||
|
local html="$1"
|
||||||
|
|
||||||
|
echo "$html" \
|
||||||
|
| grep "\"name\": " \
|
||||||
|
| sed 's/.*"name": "//' \
|
||||||
|
| sed 's/".*//'
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Get the URL to a video uploader's channel, from HTML
|
||||||
|
function video_author_url {
|
||||||
|
local html="$1"
|
||||||
|
|
||||||
|
local author_name="$(video_author_name "$html")"
|
||||||
|
local relative_url="$(echo "$html" \
|
||||||
|
| grep "$author_name" \
|
||||||
|
| grep "channel" \
|
||||||
|
| grep "href" \
|
||||||
|
| sed 's%.*="/%/%' \
|
||||||
|
| sed 's/".*//')"
|
||||||
|
echo "https://youtube.com${relative_url}"
|
||||||
|
}
|
||||||
|
|
||||||
|
# STRING --> STRING
|
||||||
|
# Get the title of a video, from HTML.
|
||||||
|
function video_title {
|
||||||
|
local html="$1"
|
||||||
|
|
||||||
|
echo "$html" \
|
||||||
|
| grep "meta name=\"title\"" \
|
||||||
|
| sed 's/.*content="//' \
|
||||||
|
| sed 's/".*//' \
|
||||||
|
| sed 's/ - Youtube//'
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
# --------------------------------------
|
||||||
|
|
||||||
|
# STRING STRING --> STRING
|
||||||
|
# Display results from a string of result_lines and a format-option
|
||||||
|
function results_display {
|
||||||
|
local result_lines="$1"
|
||||||
|
local format="$2"
|
||||||
|
|
||||||
|
IFS='
|
||||||
|
'
|
||||||
|
|
||||||
|
for result in $result_lines; do
|
||||||
|
case "$format" in
|
||||||
|
"compact") result_format_compact "$result" ;;
|
||||||
|
"small") result_format_small "$result" ;;
|
||||||
|
"medium") result_format_medium "$result" ;;
|
||||||
|
"big") result_format_big "$result" ;;
|
||||||
|
esac
|
||||||
|
done
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
# --------------------------------------
|
||||||
|
# playlist usage
|
||||||
|
|
||||||
|
# Print playlist usage.
|
||||||
|
function playlist_list_usage {
|
||||||
|
echo "usage: yt playlist --list [-csmb] url/id"
|
||||||
|
exit 2
|
||||||
|
}
|
||||||
|
|
||||||
|
# Print playlist usage.
|
||||||
|
function playlist_search_usage {
|
||||||
|
echo "usage: yt playlist --search [-csmb] search_query"
|
||||||
|
exit 2
|
||||||
|
}
|
||||||
|
|
||||||
|
# Print playlist usage.
|
||||||
|
function playlist_views_usage {
|
||||||
|
echo "usage: yt playlist --views url/id"
|
||||||
|
exit 2
|
||||||
|
}
|
||||||
|
|
||||||
|
# Print playlist usage.
|
||||||
|
function playlist_author_usage {
|
||||||
|
echo "usage: yt playlist --author [-un] url/id"
|
||||||
|
exit 2
|
||||||
|
}
|
||||||
|
|
||||||
|
# Print playlist usage.
|
||||||
|
function playlist_date_usage {
|
||||||
|
echo "usage: yt playlist --date url/id"
|
||||||
|
exit 2
|
||||||
|
}
|
||||||
|
|
||||||
|
# Print playlist usage.
|
||||||
|
function playlist_title_usage {
|
||||||
|
echo "usage: yt playlist --title url/id"
|
||||||
|
exit 2
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
# --------------------------------------
|
||||||
|
# playlist invocation
|
||||||
|
|
||||||
|
# Invoke the playlist --list command
|
||||||
|
function playlist_list_invocation {
|
||||||
|
if test "$1" = "-h" -o "$1" = "--help"; then playlist_list_usage; fi
|
||||||
|
|
||||||
|
if test -n "$2"; then
|
||||||
|
local url="$2"
|
||||||
|
case "$1" in
|
||||||
|
"-c") local format="compact" ;;
|
||||||
|
"-s") local format="small" ;;
|
||||||
|
"-m") local format="medium" ;;
|
||||||
|
"-b") local format="big" ;;
|
||||||
|
esac
|
||||||
|
else
|
||||||
|
local url="$1"
|
||||||
|
local format="big"
|
||||||
|
fi
|
||||||
|
|
||||||
|
if echo "$url" | grep -qv "youtube.com"; then
|
||||||
|
url="https://www.youtube.com/playlist?list=${url}"
|
||||||
|
fi
|
||||||
|
|
||||||
|
playlist_html="$(gendl "$url")"
|
||||||
|
result_lines="$(result_lines "$playlist_html")"
|
||||||
|
|
||||||
|
results_display "$result_lines" "$format"
|
||||||
|
}
|
||||||
|
|
||||||
|
# Invoke the playlist --search command
|
||||||
|
function playlist_search_invocation {
|
||||||
|
if test "$1" = "-h" -o "$1" = "--help"; then playlist_search_usage; fi
|
||||||
|
|
||||||
|
if test -n "$2"; then
|
||||||
|
local query="$2"
|
||||||
|
case "$1" in
|
||||||
|
"-c") local format="compact" ;;
|
||||||
|
"-s") local format="small" ;;
|
||||||
|
"-m") local format="medium" ;;
|
||||||
|
"-b") local format="big" ;;
|
||||||
|
esac
|
||||||
|
else
|
||||||
|
local query="$1"
|
||||||
|
local format="big"
|
||||||
|
fi
|
||||||
|
|
||||||
|
query="$(echo "$query" | sed 's/ /+/g')"
|
||||||
|
|
||||||
|
local search_url="https://youtube.com/results?search_query=${query}"
|
||||||
|
search_url="${search_url}&sp=EgIQAw%253D%253D"
|
||||||
|
|
||||||
|
local search_html="$(gendl "$search_url")"
|
||||||
|
local result_lines="$(result_lines "$search_html")"
|
||||||
|
|
||||||
|
results_display "$result_lines" "$format"
|
||||||
|
}
|
||||||
|
|
||||||
|
# Invoke playlist --title
|
||||||
|
function playlist_title_invocation {
|
||||||
|
if test "$1" = "-h" -o "$1" = "--help"; then playlist_title_usage; fi
|
||||||
|
|
||||||
|
local url="$1"
|
||||||
|
|
||||||
|
playlist_title "$(gendl "$url")"
|
||||||
|
}
|
||||||
|
|
||||||
|
# Invoke playlist --desc
|
||||||
|
function playlist_desc_invocation {
|
||||||
|
if test "$1" = "-h" -o "$1" = "--help"; then playlist_desc_usage; fi
|
||||||
|
|
||||||
|
if echo "$1" | grep "youtube" > /dev/null; then URL="$1"
|
||||||
|
else
|
||||||
|
URL="https://www.youtube.com/playlist?list=${1}"
|
||||||
|
fi
|
||||||
|
|
||||||
|
playlist_desc "$(gendl "$URL")"
|
||||||
|
}
|
||||||
|
|
||||||
|
# Invoke playlist --views
|
||||||
|
function playlist_views_invocation {
|
||||||
|
case "$1" in
|
||||||
|
"-h") playlist_views_usage ;;
|
||||||
|
"--help")
|
||||||
|
playlist_views_usage ;;
|
||||||
|
*youtube*)
|
||||||
|
local url="$1" ;;
|
||||||
|
*) local url="https://www.youtube.com/playlist?list=${1}" ;;
|
||||||
|
esac
|
||||||
|
|
||||||
|
playlist_views "$(gendl "$url")"
|
||||||
|
}
|
||||||
|
|
||||||
|
# Invoke playlist --date
|
||||||
|
function playlist_uploaded_invocation {
|
||||||
|
if test "$1" = "-h" -o "$1" = "--help"; then playlist_date_usage; fi
|
||||||
|
|
||||||
|
if echo "$1" | grep "youtube" > /dev/null; then URL="$1"
|
||||||
|
else
|
||||||
|
URL="https://www.youtube.com/playlist?list=${1}"
|
||||||
|
fi
|
||||||
|
|
||||||
|
playlist_uploaded "$(gendl "$URL")"
|
||||||
|
}
|
||||||
|
|
||||||
|
# Invoke playlist --author
|
||||||
|
function playlist_author_invocation {
|
||||||
|
case "$1" in
|
||||||
|
"--help")
|
||||||
|
playlist_author_usage ;;
|
||||||
|
"-h") playlist_author_usage ;;
|
||||||
|
"-u") view="url"
|
||||||
|
url="$2"
|
||||||
|
;;
|
||||||
|
"-n") view="name"
|
||||||
|
url="$2"
|
||||||
|
;;
|
||||||
|
*) view="both"
|
||||||
|
url="$1"
|
||||||
|
;;
|
||||||
|
esac
|
||||||
|
|
||||||
|
if echo "$url" | grep -qv "youtube"; then
|
||||||
|
url="https://www.youtube.com/playlist?list=${1}"
|
||||||
|
fi
|
||||||
|
|
||||||
|
html="$(gendl "$url")"
|
||||||
|
|
||||||
|
case "$view" in
|
||||||
|
"url") playlist_author_url "$html" ;;
|
||||||
|
"name") playlist_author_name "$html" ;;
|
||||||
|
"both") echo "$(playlist_author_name "$html")"
|
||||||
|
echo "$(playlist_author_url "$html")"
|
||||||
|
;;
|
||||||
|
esac
|
||||||
|
}
|
||||||
|
|
||||||
|
# --------------------------------------
|
||||||
|
# video usage
|
||||||
|
|
||||||
|
# Print video --search usage
|
||||||
|
function video_search_usage {
|
||||||
|
echo "usage: yt video --search [-csmb] query"
|
||||||
|
exit 2
|
||||||
|
}
|
||||||
|
|
||||||
|
# Print video --desc usage
|
||||||
|
function video_desc_usage {
|
||||||
|
echo "usage: yt video --desc url/id"
|
||||||
|
exit 2
|
||||||
|
}
|
||||||
|
|
||||||
|
# Print video --views usage
|
||||||
|
function video_views_usage {
|
||||||
|
echo "usage: yt video --views url/id"
|
||||||
|
exit 2
|
||||||
|
}
|
||||||
|
|
||||||
|
# Print video --author usage
|
||||||
|
function video_author_usage {
|
||||||
|
echo "usage: yt video --author [-un] url/id"
|
||||||
|
exit 2
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
# --------------------------------------
|
||||||
|
# video invocation
|
||||||
|
|
||||||
|
# Invoke video --search
|
||||||
|
function video_search_invocation {
|
||||||
|
if test "$1" = "-h" -o "$1" = "--help"; then video_search_usage; fi
|
||||||
|
|
||||||
|
if test -n "$2"; then
|
||||||
|
local query="$2"
|
||||||
|
case "$1" in
|
||||||
|
"-c") local format="compact" ;;
|
||||||
|
"-s") local format="small" ;;
|
||||||
|
"-m") local format="medium" ;;
|
||||||
|
"-b") local format="big" ;;
|
||||||
|
esac
|
||||||
|
else
|
||||||
|
local query="$1"
|
||||||
|
local format="big"
|
||||||
|
fi
|
||||||
|
|
||||||
|
query="$(echo "$query" | sed 's/ /+/g')"
|
||||||
|
|
||||||
|
local search_url="https://youtube.com/results?search_query=${query}"
|
||||||
|
search_url="${search_url}&sp=EgIQAQ%253D%253D"
|
||||||
|
|
||||||
|
local search_html="$(gendl "$search_url")"
|
||||||
|
local result_lines="$(result_lines "$search_html")"
|
||||||
|
|
||||||
|
results_display "$result_lines" "$format"
|
||||||
|
}
|
||||||
|
|
||||||
|
# Invoke video --title
|
||||||
|
function video_title_invocation {
|
||||||
|
if test "$1" = "-h" -o "$1" = "--help"; then video_title_usage; fi
|
||||||
|
|
||||||
|
local url="$1"
|
||||||
|
|
||||||
|
video_title "$(gendl "$url")"
|
||||||
|
}
|
||||||
|
|
||||||
|
# Invoke video --desc
|
||||||
|
function video_desc_invocation {
|
||||||
|
if test "$1" = "-h" -o "$1" = "--help"; then video_desc_usage; fi
|
||||||
|
|
||||||
|
if echo "$1" | grep "youtube" > /dev/null; then URL="$1"
|
||||||
|
else
|
||||||
|
URL="https://www.youtube.com/watch?v=${1}"
|
||||||
|
fi
|
||||||
|
|
||||||
|
video_desc "$(gendl "$URL")"
|
||||||
|
}
|
||||||
|
|
||||||
|
# Invoke video --date
|
||||||
|
function video_uploaded_invocation {
|
||||||
|
if test "$1" = "-h" -o "$1" = "--help"; then video_date_usage; fi
|
||||||
|
|
||||||
|
if echo "$1" | grep "youtube" > /dev/null; then URL="$1"
|
||||||
|
else
|
||||||
|
URL="https://www.youtube.com/watch?v=${1}"
|
||||||
|
fi
|
||||||
|
|
||||||
|
video_uploaded "$(gendl "$URL")"
|
||||||
|
}
|
||||||
|
|
||||||
|
# Invoke video --views
|
||||||
|
function video_views_invocation {
|
||||||
|
case "$1" in
|
||||||
|
"-h") video_views_usage ;;
|
||||||
|
"--help")
|
||||||
|
video_views_usage ;;
|
||||||
|
*youtube*)
|
||||||
|
local url="$1" ;;
|
||||||
|
*) local url="https://www.youtube.com/watch?v=${1}" ;;
|
||||||
|
esac
|
||||||
|
|
||||||
|
video_views "$(gendl "$url")"
|
||||||
|
}
|
||||||
|
|
||||||
|
# Invoke video --author
|
||||||
|
function video_author_invocation {
|
||||||
|
case "$1" in
|
||||||
|
"--help")
|
||||||
|
video_author_usage ;;
|
||||||
|
"-h") video_author_usage ;;
|
||||||
|
"-u") view="url"
|
||||||
|
url="$2"
|
||||||
|
;;
|
||||||
|
"-n") view="name"
|
||||||
|
url="$2"
|
||||||
|
;;
|
||||||
|
*) view="both"
|
||||||
|
url="$1"
|
||||||
|
;;
|
||||||
|
esac
|
||||||
|
|
||||||
|
if echo "$url" | grep -qv "youtube"; then
|
||||||
|
url="https://www.youtube.com/watch?v=${1}"
|
||||||
|
fi
|
||||||
|
|
||||||
|
html="$(gendl "$url")"
|
||||||
|
|
||||||
|
case "$view" in
|
||||||
|
"url") video_author_url "$html" ;;
|
||||||
|
"name") video_author_name "$html" ;;
|
||||||
|
"both") echo "$(video_author_name "$html")"
|
||||||
|
echo "$(video_author_url "$html")"
|
||||||
|
;;
|
||||||
|
esac
|
||||||
|
}
|
Reference in New Issue