roboflow/supervision · error · BackendUnavailableError

PyAV fallback supports file paths, not webcam device indexes

Error message

PyAV fallback supports file paths, not webcam device indexes.

What it means

BackendUnavailableError raised by the PyAV VideoCapture fallback when the source is an integer device index. PyAV can only demux files/URLs; it has no V4L2/DSHOW camera access, so webcam indices are rejected explicitly instead of hanging or failing obscurely.

Source

Thrown at src/supervision/_cv2/_video.py:75


class _VideoCapture:
    """Expose OpenCV-shaped file capture backed by PyAV decoding."""

    def __init__(self, source: str | os.PathLike[str] | int) -> None:
        """Open a file source and retain a lazy PyAV frame iterator."""
        self._container: Any = None
        self._stream: Any = None
        self._frames: Iterator[Any] | None = None
        self._source = source
        self._position = 0
        self._frame_count_cache: int | None = None
        self._opened = False
        self._error: Exception | None = None

        try:
            if isinstance(source, int):
                raise BackendUnavailableError(
                    "PyAV fallback supports file paths, not webcam device indexes."
                )
            self._container = av.open(str(source), mode="r")
            if not self._container.streams.video:
                raise ValueError(f"Video source has no video stream: {source}")
            self._stream = self._container.streams.video[0]
            self._frames = iter(self._container.decode(video=self._stream.index))
            self._opened = True
        except Exception as exc:
            self._error = exc
            logger.warning("Failed to open video source %r: %s", source, exc)
            self.release()

    def isOpened(self) -> bool:
        """Return whether the underlying video file is open for reading."""
        return self._opened

    def _frame_count(self) -> int:

View on GitHub (pinned to 7f254d9784)

Solutions

  1. Install opencv-python (headless is insufficient for webcams on some platforms; use opencv-python plus v4l2 on Linux) to get real capture backends.
  2. If you only need file/HTTP video, pass a path or URL string instead of an index.
  3. Gate webcam features: detect the fallback via try-import cv2 and disable camera input in that environment.

Example fix

# before
cap = cv2.VideoCapture(0)  # webcam — fails on PyAV fallback

# after
# environment fix
pip install opencv-python
cap = cv2.VideoCapture(0)
Defensive patterns

Strategy: validation

Validate before calling

def open_source(source):
    if isinstance(source, int):
        try:
            import cv2  # noqa: F401
        except ImportError:
            raise RuntimeError('webcam requires opencv-python; PyAV fallback supports files only')
    return cv2.VideoCapture(source)

Try / catch

try:
    cap = cv2.VideoCapture(source)
except Exception as e:
    if 'webcam device indexes' in str(e):
        raise RuntimeError('install opencv-python for webcam support') from e
    raise

Prevention

When it happens

Trigger: cv2.VideoCapture(0) or any integer device index in an environment where opencv-python is missing and Supervision substitutes its PyAV capture.

Common situations: Running webcam demos in slim Docker containers or CI where opencv-python was removed to shrink the image; PyAV is present (or installed as Supervision's media fallback) but no camera backend exists.

Related errors


AI-assisted analysis of roboflow/supervision@7f254d9784 (2026-08-15). Data as JSON: /api/errors/59e666dd0b6e592e. Report an issue: GitHub.