Spaces:
Running
Running
File size: 3,643 Bytes
58f00c9 84e63a1 58f00c9 84e63a1 5f400f8 58f00c9 84e63a1 58f00c9 | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 | import json
import logging
import os
import shutil
import subprocess
import sys
from pathlib import Path
import pytest
sys.path.insert(0, str(Path(__file__).resolve().parent.parent))
from bot.errorlog import ChannelLogHandler # noqa: E402
from .appkit import ctx # noqa: E402 the handler-level fixture, shared by every test module
__all__ = ["ctx", "needs_ffmpeg"]
HAVE_FFMPEG = shutil.which("ffmpeg") is not None and shutil.which("ffprobe") is not None
needs_ffmpeg = pytest.mark.skipif(not HAVE_FFMPEG, reason="ffmpeg/ffprobe not installed")
@pytest.fixture(autouse=True)
def _no_stray_error_reporters():
"""A test that stops halfway must not leave an error reporter on the root logger for the tests after it."""
yield
for handler in [h for h in logging.getLogger().handlers if isinstance(h, ChannelLogHandler)]:
handler.detach()
SRT_A = "1\n00:00:00,000 --> 00:00:01,000\nkonnichiwa\n\n"
SRT_B = "1\n00:00:00,000 --> 00:00:01,000\nhello\n\n"
FFMETA = """;FFMETADATA1
title=Original Title
[CHAPTER]
TIMEBASE=1/1000
START=0
END=1000
title=Intro
[CHAPTER]
TIMEBASE=1/1000
START=1000
END=2000
title=Main
"""
def run(cmd):
subprocess.run(cmd, check=True, stdout=subprocess.DEVNULL, stderr=subprocess.PIPE)
def ffprobe_json(path, *extra):
out = subprocess.run(
["ffprobe", "-v", "error", "-print_format", "json", "-show_format", "-show_streams", *extra, str(path)],
check=True, capture_output=True,
).stdout
return json.loads(out)
@pytest.fixture(scope="session")
def media_dir(tmp_path_factory):
d = tmp_path_factory.mktemp("media")
if not HAVE_FFMPEG:
return d
(d / "a.srt").write_text(SRT_A)
(d / "b.srt").write_text(SRT_B)
(d / "meta.ffmeta").write_text(FFMETA)
(d / "font.ttf").write_bytes(os.urandom(2048))
lavfi_v = ["-f", "lavfi", "-i", "testsrc=duration=2:size=320x240:rate=15"]
lavfi_a = lambda f: ["-f", "lavfi", "-i", f"sine=frequency={f}:duration=2"] # noqa: E731
# MKV: 1 video, 3 audio (jpn, eng, hin), 2 subs (jpn, eng), 1 font attachment, 2 chapters
run(
["ffmpeg", "-y", "-loglevel", "error", *lavfi_v, *lavfi_a(440), *lavfi_a(880), *lavfi_a(220),
"-i", str(d / "a.srt"), "-i", str(d / "b.srt"), "-i", str(d / "meta.ffmeta"),
"-attach", str(d / "font.ttf"), "-metadata:s:t:0", "mimetype=application/x-truetype-font",
"-map", "0:v", "-map", "1:a", "-map", "2:a", "-map", "3:a", "-map", "4:s", "-map", "5:s",
"-map_metadata", "6", "-map_chapters", "6",
"-c:v", "libx264", "-preset", "ultrafast", "-c:a", "aac", "-c:s", "srt",
"-metadata:s:a:0", "language=jpn", "-metadata:s:a:0", "title=Japanese Original",
"-metadata:s:a:1", "language=eng", "-metadata:s:a:2", "language=hin",
"-metadata:s:s:0", "language=jpn", "-metadata:s:s:1", "language=eng",
"-disposition:a:0", "default", str(d / "sample.mkv")]
)
# MP4: 1 video, 2 audio (jpn, eng), 1 eng subtitle (mov_text)
run(
["ffmpeg", "-y", "-loglevel", "error", *lavfi_v, *lavfi_a(440), *lavfi_a(880), "-i", str(d / "b.srt"),
"-map", "0:v", "-map", "1:a", "-map", "2:a", "-map", "3:s",
"-c:v", "libx264", "-preset", "ultrafast", "-pix_fmt", "yuv420p", "-c:a", "aac", "-c:s", "mov_text",
"-metadata:s:a:0", "language=jpn", "-metadata:s:a:1", "language=eng", "-metadata:s:s:0", "language=eng",
str(d / "sample.mp4")]
)
# MP3 with a title tag
run(
["ffmpeg", "-y", "-loglevel", "error", *lavfi_a(440), "-c:a", "libmp3lame", "-metadata", "title=Old",
str(d / "sample.mp3")]
)
return d
|