Spaces:
Sleeping
Sleeping
import gradio as gr | |
from pytube import YouTube | |
from pytube.exceptions import RegexMatchError, VideoUnavailable | |
import os | |
import subprocess | |
def download_media(url, resolution, media_format): | |
try: | |
yt = YouTube(url) | |
output_path = "downloads" | |
os.makedirs(output_path, exist_ok=True) | |
# Очищаем название файла от недопустимых символов | |
title = "".join(c for c in yt.title if c.isalnum() or c in (' ', '_')).rstrip() | |
if media_format == "mp3": | |
audio_stream = yt.streams.get_audio_only() | |
out_file = audio_stream.download(output_path=output_path, filename=title) | |
base, _ = os.path.splitext(out_file) | |
new_file = f"{base}.mp3" | |
os.rename(out_file, new_file) | |
return new_file | |
else: # mp4 | |
if resolution in ["1080p", "4k"]: | |
# Для высоких разрешений | |
video_stream = yt.streams.filter(res=resolution, file_extension="mp4", type="video").first() | |
audio_stream = yt.streams.get_audio_only() | |
if not video_stream or not audio_stream: | |
raise Exception("Required streams not found") | |
video_path = video_stream.download(output_path=output_path, filename_prefix="video_") | |
audio_path = audio_stream.download(output_path=output_path, filename_prefix="audio_") | |
output_file = os.path.join(output_path, f"{title}.mp4") | |
subprocess.run([ | |
'ffmpeg', '-i', video_path, '-i', audio_path, | |
'-c:v', 'copy', '-c:a', 'aac', '-strict', 'experimental', | |
output_file | |
], check=True) | |
os.remove(video_path) | |
os.remove(audio_path) | |
return output_file | |
else: | |
stream = yt.streams.filter(res=resolution, file_extension="mp4", progressive=True).first() | |
if not stream: | |
raise Exception("Stream not found") | |
return stream.download(output_path=output_path, filename=title + ".mp4") | |
except Exception as e: | |
print(f"Error: {str(e)}") | |
return None # Возвращаем None вместо строки с ошибкой | |
# Создаем интерфейс с отдельным компонентом для ошибок | |
with gr.Blocks() as app: | |
gr.Markdown("## YouTube Video Downloader") | |
with gr.Row(): | |
url = gr.Textbox(label="YouTube URL") | |
resolution = gr.Dropdown(["144p", "360p", "720p", "1080p", "4k"], label="Resolution") | |
media_format = gr.Dropdown(["mp4", "mp3"], label="Format") | |
download_button = gr.Button("Download") | |
output_file = gr.File(label="Downloaded File") | |
error_output = gr.Textbox(label="Error Message", visible=False) | |
def handle_download(url, resolution, media_format): | |
result = download_media(url, resolution, media_format) | |
if result and os.path.exists(result): | |
return [result, gr.Textbox(visible=False)] | |
return [None, gr.Textbox(value="Error: Failed to download. Possible reasons:\n- Invalid URL\n- Restricted content\n- Unavailable format", visible=True)] | |
download_button.click( | |
fn=handle_download, | |
inputs=[url, resolution, media_format], | |
outputs=[output_file, error_output] | |
) | |
if __name__ == "__main__": | |
app.launch(share=True) # Добавлен параметр share=True |