From 703d60dd43fd14f6facd35a06c7e9ccb2145d504 Mon Sep 17 00:00:00 2001 From: Fedor Sevrugin Date: Tue, 21 Jan 2025 03:18:48 +0300 Subject: [PATCH] V1.0 --- README.md | 14 ++++++++ fedordowntube.py | 93 ++++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 107 insertions(+) create mode 100644 fedordowntube.py diff --git a/README.md b/README.md index e69de29..6f8a887 100644 --- a/README.md +++ b/README.md @@ -0,0 +1,14 @@ +FedorDownTube — программа для скачивания видео с ютуба с учётом блокировок. Для доступа к видео, необходимо иметь запущенный fedordpi. На данный момент работает только под Linux. + +Зависимости: +1)pytubefix: pip install pytubefix +2)ffmpeg +3)fedordpi + +Использование: +Запуск: python3 fedordowntube.py [URL] # URL опционален, если его не указать, его всё равно спросит +После запуска будут предложенны возможные варианты качества, указать нужный пункт можно номером в списке или написать 1080 или 1080p. Будут скачаны отдельно фаил видео и звука, а затем перекодированны в mp4 при помощи ffmpeg. + +На первом запуске и раз в какоето время будет спрашивать PoToken и visitorData. Это нужно для обхода антиботсистемы ютуба. Гайд как получить эти значения вот: https://github.com/JuanBindez/pytubefix/pull/209 + +Известные проблемы: Иногда зависает на этапе скачивания видео или видео, помогает перезапуск или выбор другого качества. diff --git a/fedordowntube.py b/fedordowntube.py new file mode 100644 index 0000000..05f94f8 --- /dev/null +++ b/fedordowntube.py @@ -0,0 +1,93 @@ +import os +from sys import argv +from pytubefix import YouTube +from pytubefix.cli import on_progress + + +def combine(audio: str, video: str, output: str) -> None: + + if os.path.exists(output): + os.remove(output) + + code = os.system(f'ffmpeg -i "{video}" -i "{audio}" -c copy "{output}"') + + if code != 0: + raise SystemError(code) + + +def download(yt, choice): + + video_stream = yt.streams.\ + filter(type='video', mime_type="video/webm", progressive=False).\ + order_by('resolution').\ + desc()[choice] + + audio_stream = yt.streams.\ + filter(mime_type='audio/mp4').\ + order_by('filesize').\ + desc().first() + + print('Information:') + print("\tTitle:", yt.title) + print("\tAuthor:", yt.author) + print("\tDate:", yt.publish_date) + print("\tResolution:", video_stream.resolution) + print("\tViews:", yt.views) + print("\tLength:", round(yt.length/60), "minutes") + print("\tFilename of the video:", video_stream.default_filename) + print("\tFilesize of the video:", round( + video_stream.filesize / 1000000), "MB") + + print('Download video...') + video_stream.download() + print('\nDownload audio...') + audio_stream.download() + + combine(audio_stream.default_filename, video_stream.default_filename, f'{yt.title}.mp4') + + +def menu(url: str): + + yt = YouTube( + proxies={"http": "http://127.0.0.1:8881", + "https": "http://127.0.0.1:8881"}, + url=url, + on_progress_callback=on_progress, + use_po_token=True, + ) + + available_res = [i for i in (yt.streams.\ + filter(type='video', mime_type="video/webm", progressive=False).\ + order_by('resolution').\ + desc())] + + j = 0 + for i in available_res: + j += 1 + print(str(j) + ')', i.resolution, '(' + str(i.fps), 'fps)') + + while True: + choice = input('\n>>> ') + try: + if choice in available_res: + res = available_res.index(choice) + break + elif (choice + 'p') in available_res: + res = available_res.index(choice + 'p') + break + elif int(choice) in range(1, j+1): + res = int(choice) - 1 + break + else: + print('not found') + except: + print('exc not found') + + download(yt, res) + + +if len(argv) == 2: + url = argv[1] +else: + url = input("url: ") +menu(url) -- 2.30.2