Как правильно передать имя файла с одинарной кавычкой в ​​фильтр субтитров ffmpeg в Python?Python

Программы на Python
Anonymous
 Как правильно передать имя файла с одинарной кавычкой в ​​фильтр субтитров ffmpeg в Python?

Сообщение Anonymous »

Я пишу скрипт Python с использованием подпроцесса для жесткого кодирования субтитров к видео. Мой код создает сложный граф фильтров для аргумента -vf ffmpeg, который включает в себя запись нескольких слоев стилизованных субтитров из файла SRT.
Сценарий отлично работает для большинства файлов, но он терпит неудачу всякий раз, когда имя файла субтитров содержит одну кавычку (апостроф), например, Вот и все.srt.
Когда скрипт встречает такой файл, Процесс ffmpeg немедленно завершается с ошибкой и не создает выходной файл. Это вызывает ошибку нисходящего потока KeyError: 'streams' в моем коде, когда он позже пытается запустить ffprobe для несуществующего выходного файла, но основной причиной является молчаливый сбой команды ffmpeg.
Единственное решение, которое я нашел, - это программно переименовать файл, чтобы удалить апостроф, чего я хочу избежать.
В первый раз, когда я столкнулся с этим, я прочитал вывел журнал и увидел, что ffmpeg сам удаляет апострофы из пути к строке, передаваемого в ffmpeg в коде.

Код: Выделить всё

[Parsed_subtitles_1 @ 000002c435dce5c0] Unable to open C:/FUBAR/Season 01/FUBAR - S01E08 - Thats It and Thats All.srt
Код
Вот упрощенный пример того, как строка фильтра -vf и последняя команда ffmpeg создаются в моем скрипте:

Код: Выделить всё

import subprocess
from pathlib import Path

# --- Example of a problematic file path ---
source_video_path = Path(r"C:\videos\FUBAR - S01E08 - That's It and That's All.mkv")
subtitle_path = source_video_path.with_suffix('.srt')

# --- This is how I build the filter string ---
video_filter = 'crop=1920:800:0:140' # Example starting filter

# The subtitle path is formatted for the filter string
# NOTE: My real code finds this path dynamically.
formatted_subtitle_path = str(subtitle_path).replace('\\', '/')

# A simplified version of my style loop
style_string = "FontName=Segoe UI,FontSize=18,PrimaryColour=&H00FFFFFF"

# The filename is placed inside single quotes in the filter
video_filter += f",subtitles=filename='{formatted_subtitle_path}':force_style='{style_string}'"

# --- The final ffmpeg command list ---
command = [
'ffmpeg.exe',
'-y',
'-i', str(source_video_path),
'-vf', video_filter,
'-c:a', 'copy',
'output.mkv',
]

print("--- Generated FFmpeg Command ---")
# Using print to show how Python sees the arguments before execution
for i, arg in enumerate(command):
print(f"Arg[{i}]: {arg}")

# When run, ffmpeg fails on this command because of the ' in the filename.
# process = subprocess.run(command, text=True, capture_output=True)
# print("\n--- FFmpeg Output ---")
# print(process.stderr)
Что я пробовал
Я понимаю, что проблема в том, что одинарная кавычка в «Вот и все» преждевременно завершает строку filename='...' в фильтре -vf. Я пробовал несколько распространенных методов, чтобы избежать его, но ни один из них не сработал:
  • Эскейпирование обратной косой черты: Я пробовал заменить апостроф в formatted_subtitle_path различными escape-последовательностями перед созданием строки фильтра.
  • Трюк с цитированием оболочки: Я также попробовал метод '''.

    Код: Выделить всё

    replace("'", r"'\''")
  • Использование двойных кавычек: Я попытался изменить строку фильтра, чтобы заключить имя файла в двойные кавычки, но ffmpeg по-прежнему не работает.

Код: Выделить всё

video_filter += f""",subtitles=filename="{formatted_subtitle_path}":force_style=...
Ни одна из этих попыток не увенчалась успехом; процесс ffmpeg всегда не запускается или немедленно выдает ошибку.
Каков наиболее эффективный кроссплатформенный способ форматирования строки имени файла для фильтра субтитров ffmpeg, чтобы он мог правильно обрабатывать пути, содержащие одинарные кавычки?

Подробнее здесь: https://stackoverflow.com/questions/797 ... tles-filte

Вернуться в «Python»