Skip to content

Commit

Permalink
Allow using pathlib.Path for av.open
Browse files Browse the repository at this point in the history
  • Loading branch information
WyattBlue committed Nov 22, 2023
1 parent cf8a5c3 commit 39832c4
Show file tree
Hide file tree
Showing 2 changed files with 76 additions and 26 deletions.
67 changes: 41 additions & 26 deletions av/container/core.pyx
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
from cython.operator cimport dereference
from libc.stdint cimport int64_t

from pathlib import Path
import os
import time

Expand Down Expand Up @@ -334,10 +335,19 @@ cdef class Container:
auto_bsf = flags.flag_property('AUTO_BSF')


def open(file, mode=None, format=None, options=None,
container_options=None, stream_options=None,
metadata_encoding='utf-8', metadata_errors='strict',
buffer_size=32768, timeout=None, io_open=None):
def open(
file,
mode=None,
format=None,
options=None,
container_options=None,
stream_options=None,
metadata_encoding="utf-8",
metadata_errors="strict",
buffer_size=32768,
timeout=None,
io_open=None,
):
"""open(file, mode='r', **kwargs)
Main entrypoint to opening files/streams.
Expand Down Expand Up @@ -385,34 +395,39 @@ def open(file, mode=None, format=None, options=None,
`FFmpeg website <https://www.ffmpeg.org/ffmpeg-devices.html>`_.
"""

if not (mode is None or (isinstance(mode, str) and mode == "r" or mode == "w")):
raise ValueError(f"mode must be 'r', 'w', or None, got: {mode}")

if isinstance(file, str):
pass
elif isinstance(file, Path):
file = f"{file}"
elif mode is None:
mode = getattr(file, "mode", None)

if mode is None:
mode = getattr(file, 'mode', None)
if mode is None:
mode = 'r'
mode = "r"

if isinstance(timeout, tuple):
open_timeout = timeout[0]
read_timeout = timeout[1]
if not len(timeout) == 2:
raise ValueError("timeout must be `float` or `tuple[float, float]`")

open_timeout, read_timeout = timeout
else:
open_timeout = timeout
read_timeout = timeout

if mode.startswith('r'):
return InputContainer(
_cinit_sentinel, file, format, options,
container_options, stream_options,
metadata_encoding, metadata_errors,
buffer_size, open_timeout, read_timeout,
io_open
if mode.startswith("r"):
return InputContainer(_cinit_sentinel, file, format, options,
container_options, stream_options, metadata_encoding, metadata_errors,
buffer_size, open_timeout, read_timeout, io_open,
)
if mode.startswith('w'):
if stream_options:
raise ValueError("Provide stream options via Container.add_stream(..., options={}).")
return OutputContainer(
_cinit_sentinel, file, format, options,
container_options, stream_options,
metadata_encoding, metadata_errors,
buffer_size, open_timeout, read_timeout,
io_open

if stream_options:
raise ValueError(
"Provide stream options via Container.add_stream(..., options={})."
)
raise ValueError("mode must be 'r' or 'w'; got %r" % mode)
return OutputContainer(_cinit_sentinel, file, format, options,
container_options, stream_options, metadata_encoding, metadata_errors,
buffer_size, open_timeout, read_timeout, io_open,
)
35 changes: 35 additions & 0 deletions tests/test_open.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
from pathlib import Path

import av

from .common import TestCase, fate_suite


class TestOpen(TestCase):
def test_path_input(self):
path = Path(fate_suite("h264/interlaced_crop.mp4"))
self.assertIsInstance(path, Path)

container = av.open(path)
self.assertIs(type(container), av.container.InputContainer)

def test_str_input(self):
path = fate_suite("h264/interlaced_crop.mp4")
self.assertIs(type(path), str)

container = av.open(path)
self.assertIs(type(container), av.container.InputContainer)

def test_path_output(self):
path = Path(fate_suite("h264/interlaced_crop.mp4"))
self.assertIsInstance(path, Path)

container = av.open(path, "w")
self.assertIs(type(container), av.container.OutputContainer)

def test_str_output(self):
path = fate_suite("h264/interlaced_crop.mp4")
self.assertIs(type(path), str)

container = av.open(path, "w")
self.assertIs(type(container), av.container.OutputContainer)

0 comments on commit 39832c4

Please sign in to comment.