在 Python 中从 MP4 转换为 MP3 时出现 FFmpeg 错误

问题描述 投票:0回答:1

当我尝试转换 YouTube 播放列表中的视频时,出现错误:

文件“C:\Users onti\AppData\Local\Programs\Python\Python310\lib\site-packages fmpy.py”,第 106 行,运行中 引发 FFRuntimeError(self.cmd, self.process.returncode, out[0], out[1]) ffmpy.FFRuntimeError:

C:/ffmpeg/bin/ffmpeg.exe -i "Nightcore - To Be Human // lyrics.mp4" "Nightcore - To Be Human // lyrics.mp3"
已退出,状态为 1

我正在使用的代码:

from pytube import Playlist
import ffmpy
from ffmpy import FFmpeg

playlistLink = input("Introduz o link da Playlist: ")
playlist = Playlist(playlistLink)   

diretório = 'E'
while diretório != 'M' and diretório != 'V':
    diretório = input("Vais baixar música ou vídeos? (M/V)")
    if diretório == 'M':
        downloadDirectory = "C:/Users/fonti/Documents/Projetos Python/Youtube/Músicas"
    elif diretório == 'V':
        downloadDirectory = "C:/Users/fonti/Documents/Projetos Python/Youtube/Vídeos"

print("Número total de vídeos a baixar: ", len(playlist.video_urls))    

print("\n\n Links dos vídeos:\n")

for url in playlist.video_urls:
    print(url) 

def MP3():
    for video in playlist.videos:

        audio = video.streams.get_audio_only()
    
        audio.download(downloadDirectory)

        videoTitle = video.title
    
        new_filename = videoTitle + '.mp3'
        default_filename = videoTitle + '.mp4'
    
        print(default_filename+'\n\n'+new_filename)

        ff = ffmpy.FFmpeg(
            executable = 'C:/ffmpeg/bin/ffmpeg.exe',
            inputs={default_filename : None},
            outputs={new_filename : None}
        )
        ff.run()


def MP4():
    for video in playlist.videos:
        print('Downloading : {} with url : {}'.format(video.title, video.watch_url))
        video.streams.\
            filter(type='video', progressive=True, file_extension='mp4').\
            order_by('resolution').\
            desc().\
            first().\
            download(downloadDirectory)

escolha = 'E'
while escolha != 'V' and escolha != 'A':
    escolha = input("Queres formato de vídeo ou áudio (V/A)? ")
    if escolha == 'V':
        MP4()
    elif escolha == 'A':
        MP3()
    else:
        print("Escolha inválida")

如果我尝试从播放列表下载视频,效果很好。但是当我尝试下载音频时,它给了我错误。

python ffmpeg pytube
1个回答
1
投票

我们可以使用完整路径,以便 FFmpeg 可以找到文件。
我们可以将

downloadDirectory
videoTitle
连接起来以创建完整路径:

def MP3():
        ...
        videoTitle = video.title

        videoTitle = os.path.join(downloadDirectory, videoTitle)

        new_filename = videoTitle + '.mp3'
        ...

完整代码示例:

from pytube import Playlist
import ffmpy
from ffmpy import FFmpeg
import os

playlistLink = 'https://www.youtube.com/playlist?list=PLS1QulWo1RIaJECMeUT4LFwJ-ghgoSH6n' #input("Introduz o link da Playlist: ")
playlist = Playlist(playlistLink)   

diretório = 'E'
while diretório != 'M' and diretório != 'V':
    diretório = 'M' #input("Vais baixar música ou vídeos? (M/V)")
    if diretório == 'M':
        downloadDirectory = "C:/Users/fonti/Documents/Projetos Python/Youtube/Músicas"
    elif diretório == 'V':
        downloadDirectory = "C:/Users/fonti/Documents/Projetos Python/Youtube/Vídeos"

print("Número total de vídeos a baixar: ", len(playlist.video_urls))    

print("\n\n Links dos vídeos:\n")

for url in playlist.video_urls:
    print(url) 

def MP3():
    for video in playlist.videos:

        audio = video.streams.get_audio_only()
    
        audio.download(downloadDirectory)

        videoTitle = video.title

        videoTitle = os.path.join(downloadDirectory, videoTitle)  # Concatenate the directory and the file name
    
        new_filename = videoTitle + '.mp3'
        default_filename = videoTitle + '.mp4'        
    
        print(default_filename+'\n\n'+new_filename)

        ff = ffmpy.FFmpeg(
            executable = 'C:/ffmpeg/bin/ffmpeg.exe',
            inputs={default_filename : None},
            outputs={new_filename : None}
        )
        ff.run()


def MP4():
    for video in playlist.videos:
        print('Downloading : {} with url : {}'.format(video.title, video.watch_url))
        video.streams.\
            filter(type='video', progressive=True, file_extension='mp4').\
            order_by('resolution').\
            desc().\
            first().\
            download(downloadDirectory)

escolha = 'E'
while escolha != 'V' and escolha != 'A':
    escolha = 'A' #input("Queres formato de vídeo ou áudio (V/A)? ")
    if escolha == 'V':
        MP4()
    elif escolha == 'A':
        MP3()
    else:
        print("Escolha inválida")

更稳健的解决方案,是在文件夹中搜索

.mp4
文件,并在转换为
mp3
后将其删除:

from pytube import Playlist
import ffmpy
from ffmpy import FFmpeg
import os
import glob

playlistLink = 'https://www.youtube.com/playlist?list=PLS1QulWo1RIaJECMeUT4LFwJ-ghgoSH6n' #input("Introduz o link da Playlist: ")
playlist = Playlist(playlistLink)   

diretório = 'E'
while diretório != 'M' and diretório != 'V':
    diretório = 'M' #input("Vais baixar música ou vídeos? (M/V)")
    if diretório == 'M':
        downloadDirectory = "C:/Users/fonti/Documents/Projetos Python/Youtube/Músicas"
    elif diretório == 'V':
        downloadDirectory = "C:/Users/fonti/Documents/Projetos Python/Youtube/Vídeos"

print("Número total de vídeos a baixar: ", len(playlist.video_urls))    

print("\n\n Links dos vídeos:\n")

for url in playlist.video_urls:
    print(url) 

def MP3():
    # Delete all mp4 files in Músicas folder
    mp4_files = glob.glob(os.path.join(downloadDirectory, '*.mp4'))  # dir C:/Users/fonti/Documents/Projetos Python/Youtube/Músicas/*.mp4
    for f in mp4_files:
        os.remove(f)

    for video in playlist.videos:

        audio = video.streams.get_audio_only()
    
        audio.download(downloadDirectory)

        videoTitle = video.title
        videoTitle = videoTitle.strip() # use the strip() method to remove trailing and leading spaces https://stackoverflow.com/a/10443548/4926757
       
        # List all mp4 files in the directory.
        videoTitle = glob.glob(os.path.join(downloadDirectory, '*.mp4'))  # dir C:/Users/fonti/Documents/Projetos Python/Youtube/Músicas/*.mp4
        
        #videoTitle = os.path.join(downloadDirectory, videoTitle)  # Concatenate the directory and the file name
    
        #new_filename = videoTitle + '.mp3'
        #default_filename = videoTitle + '.mp4'

        default_filename = videoTitle[0]  # Suppused to be only one mp4 file in the folder.
        new_filename = default_filename.replace('.mp4', '.mp3')  # Remplace .mp4 with .mp3
    
        print(default_filename+'\n\n'+new_filename)

        ff = ffmpy.FFmpeg(
            executable = 'C:/ffmpeg/bin/ffmpeg.exe',
            inputs={default_filename : None},
            outputs={new_filename : None}
        )
        ff.run()

        os.remove(default_filename)  # Delete the mp4 file


def MP4():
    for video in playlist.videos:
        print('Downloading : {} with url : {}'.format(video.title, video.watch_url))
        video.streams.\
            filter(type='video', progressive=True, file_extension='mp4').\
            order_by('resolution').\
            desc().\
            first().\
            download(downloadDirectory)

escolha = 'E'
while escolha != 'V' and escolha != 'A':
    escolha = 'A' #input("Queres formato de vídeo ou áudio (V/A)? ")
    if escolha == 'V':
        MP4()
    elif escolha == 'A':
        MP3()
    else:
        print("Escolha inválida")
© www.soinside.com 2019 - 2024. All rights reserved.