백그라운드 명령으로 다운로드 중인 비디오 열기

백그라운드 명령으로 다운로드 중인 비디오 열기

아래 명령은 sed를 사용하여 youtube-dl의 출력을 처리하여 비디오의 파일 이름을 얻습니다.

youtube-dl "$URL" 2> /dev/null | \
sed -n 's/^\[download\] Destination: //p; s/^\[download\] \(.*\) has already been downloade.*/\1/p'

youtube-dl이 HTML 가져오기 및 구문 분석을 마치고 비디오 다운로드를 시작한 직후(실행 시작 후 몇 초/몇 초), 다운로드가 완료되면 비디오의 파일 이름이 출력됩니다(다운로드하는 동안 접미사가 붙습니다) .part. )

따라서 문제의 핵심과 제가 막고 있는 점은 위의 명령을 백그라운드로 가져오고(계속 다운로드되도록) 표준 출력에서 ​​비디오 파일 이름을 가져와서 비디오를 여는 데 어떻게 사용할 수 있느냐는 것입니다. 다운로드가 완료되기 전에 파일을 삭제하세요.

답변1

다음을 사용할 수 있습니다 inotifywait.

$ youtube-dl "$URL" &
$ inotifywait  --event create --format '"%f"' . | xargs vlc

연결이 매우 빠른 경우(지금은 내 속도) 플레이어가 파일을 열기 전에 파일을 다운로드하고 이름을 바꿀 수 있는 경쟁 조건이 있습니다. 또한 youtube-dl오디오와 비디오를 별도로 다운로드하는 경우 잘못된 파일을 열 수도 있습니다.

답변2

read@fra-san의 의견 은 출력을 한 줄씩/절차적으로(기능적으로는 파이프가 아닌) 처리하는 데 사용할 수 있는 while 루프를 생각나게 했습니다. <연산자를 사용하여 파일의 출력을 해당 루프로 파이프 할 수 있습니다. youtube-dl 명령을 Bash 프로세스로 대체하고 추가하여 백그라운드로 보낼 수도 &있으며 while 루프는 여전히 출력을 읽을 수 있습니다(BPS가 만든 파일을 읽는 것뿐입니다).

테스트를 통해 다운로드가 완료되고 이름이 변경된 후에도 비디오를 정상적으로 계속 재생할 수 있다는 것을 발견했습니다. 이는 mpv의 기능일 수 있습니다.

#!/bin/bash
# ytdl-stream - use youtube-dl to stream videos i.e watch videos as they download
# usage: ytdl-stream [YOUTUBE_DL_OPTIONS] URL 
# you can pipe into it a command to open you video player, e.g:
# echo mpv --mute=yes | ytdl-stream -f 'best[width<=1920,height<=1080]' --write-auto-sub [URL]

test ! -t 0 && player_cmd="$(cat /dev/stdin)" || player_cmd="mpv"

while IFS="" read -r line; do
  filename=$(echo "$line" | sed -n 's/^\[download\] Destination: //p')
  if [[ -z "$filename" ]]; then
    filename=$(echo "$line" | sed -n 's/^\[download\] \(.*\) has already been downloade.*/\1/p')
    [[ -z "$filename" ]] && continue || notify-send "file already downloaded, opening.."
  else
    notify-send "downloading.."
  fi
  withoutExtensions="${filename%.*}"
  withoutExtensions="${withoutExtensions%.*}"
  if [[ -e "$filename" ]]; then
    sleep 0.5 && ($player_cmd "$filename")&
  elif [[ -e "$filename".part ]]; then
    sleep 2
    if [[ -e "$filename".part ]]; then
      notify-send "found .part after sleep again"
      ($player_cmd "$filename".part)&
    else
      sleep 0.5 && ($player_cmd "$withoutExtensions"*)&
    fi
  fi
done < <(youtube-dl "$@" 2> /dev/null)&

관련 정보