pod 3.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160
  1. #!/bin/sh
  2. POD_BASE_DIR=${POD_BASE_DIR:-~/Music/}
  3. POD_SUB_DIR=${POD_SUB_DIR:-Podcasts}
  4. show_usage() {
  5. echo "$(basename $0) [ list | play [ FILE ] | pick [-x] | pause | stop | listened | update-feeds ]" >&2
  6. }
  7. show_help() {
  8. show_usage
  9. cat <<EOF
  10. $(basename $0): Manage podcasts
  11. help : show help
  12. list : list podcast episodes
  13. play [ FILE ] : if FILE, play, picking up from where last paused/stopped
  14. pick [ -x ] : pick a podcast to play, if -x, using an X-windows picker
  15. pause : pause current episode, saving current location
  16. stop : stop current episode, saving current location
  17. listened [ FILE* ] : mark current episode as listened or if FILES mark them
  18. update-feeds : update feeds
  19. EOF
  20. }
  21. git_annex_wrap() {
  22. CUR_DIR=$(pwd)
  23. cd $POD_BASE_DIR
  24. git annex $@
  25. RET_VAL=$?
  26. cd $CUR_DIR
  27. return $RET_VAL
  28. }
  29. find_unlistened() {
  30. git_annex_wrap find --metadata "tag=unlistened" --include='Podcasts/*' --in=here
  31. }
  32. play_pod() {
  33. FILE=$1
  34. PAUSE_LOC=$(git_annex_wrap metadata -g seek_time $FILE)
  35. if [ "${#PAUSE_LOC}" -lt 1 ] ; then
  36. mpc add $FILE
  37. mpc play
  38. else
  39. mpc add $FILE
  40. mpc play
  41. mpc seek $PAUSE_LOC
  42. fi
  43. }
  44. get_cur_seek() {
  45. mpc status | \
  46. awk 'NR==2 {print $0}' |\
  47. grep -Eo '([0-9]+:)?[0-9][0-9]:[0-9][0-9]' |\
  48. head -n 1
  49. }
  50. get_cur_file() {
  51. mpc status -f '%file%' | head -n 1
  52. }
  53. set_loc() {
  54. FILE=$1
  55. SEEK=$2
  56. if echo $FILE | grep 'Podcasts/' > /dev/null ; then
  57. git_annex_wrap metadata -s "seek_time=${SEEK}" "${FILE}"
  58. fi
  59. }
  60. if [ $# -lt 1 ] ; then
  61. show_usage
  62. exit 1
  63. fi
  64. CMD=$1
  65. shift
  66. case "$CMD" in
  67. help)
  68. show_help
  69. exit
  70. ;;
  71. list)
  72. find_unlistened
  73. exit
  74. ;;
  75. play)
  76. pod stop
  77. mpc clear
  78. if [ $# -lt 1 ] ; then
  79. for item in $(find_unlistened) ; do
  80. mpc add $item
  81. done
  82. else
  83. play_pod $1
  84. fi
  85. exit
  86. ;;
  87. pick)
  88. CHOSEN_POD=''
  89. if [ "$1" == "-x" ] ; then
  90. CHOSEN_POD=$(find_unlistened | rofi -dmenu -p "podcast")
  91. else
  92. CHOSEN_POD=$(find_unlistened | fzf)
  93. fi
  94. if [ "${#CHOSEN_POD}" -gt 0 ] ; then
  95. play_pod $CHOSEN_POD
  96. fi
  97. exit
  98. ;;
  99. pause)
  100. FILE=$(get_cur_file)
  101. SEEK=$(get_cur_seek)
  102. mpc pause
  103. set_loc $FILE $SEEK
  104. exit
  105. ;;
  106. stop)
  107. FILE=$(get_cur_file)
  108. SEEK=$(get_cur_seek)
  109. mpc stop
  110. set_loc $FILE $SEEK
  111. exit
  112. ;;
  113. listened)
  114. if [ $# -lt 1 ] ; then
  115. FILE=$(get_cur_file)
  116. git_annex_wrap metadata -s tag=listened $FILE
  117. git_annex_wrap metadata -r seek_time $FILE
  118. else
  119. for FILE in $* ; do
  120. git_annex_wrap metadata -s tag=listened $FILE
  121. git_annex_wrap metadata -r seek_time $FILE
  122. done
  123. fi
  124. exit
  125. ;;
  126. update-feeds)
  127. CUR_DIR=$(pwd)
  128. cd $POD_BASE_DIR
  129. grep -v '^# ' ${POD_SUB_DIR}/podcasts-list.txt |\
  130. cut -f2 |\
  131. xargs -L1 git annex importfeed \
  132. --template="${POD_SUB_DIR}/\${feedtitle}/\${itempubdate}-\${itemtitle}\${extension}"
  133. git annex add ${POD_SUB_DIR}
  134. git commit -m "Caught podcasts"
  135. git annex find --include='Podcasts/*' --and --not --metadata tag=listened |\
  136. xargs git annex metadata --tag unlistened
  137. mpc update
  138. cd $CUR_DIR
  139. exit
  140. ;;
  141. *)
  142. show_usage
  143. echo
  144. echo "Subcommand $CMD is not valid." >&2
  145. exit 1
  146. ;;
  147. esac