from pathlib import Path
from typing import Any
from typing import Union
from typing import cast


def get_bytes(stream_or_file: Any) -> Union[bytes, str]:
    """
    Returns the bytes of the given stream or file argument. If it is a file, it will be opened
    in binary mode.

    Examples:
        >>> import tempfile
        >>> tmp = tempfile.NamedTemporaryFile()
        >>> print(get_bytes(tmp.name))
        b''
        >>> with open(tmp.name, 'rb') as stream:
        ...     get_bytes(stream)
        b''
        >>> get_bytes('thatonedoesnotexist')
        Traceback (most recent call last):
            ...
        ValueError: Argument 'stream_or_file' is neither a stream nor a file

    Args:
        stream_or_file: Stream or file to read the bytes from.

    Returns:
        Bytes of ``stream_or_file``
    """
    if getattr(stream_or_file, 'read', None):
        return cast(Union[bytes, str], stream_or_file.read())
    if Path(stream_or_file).is_file():
        with open(stream_or_file, 'rb') as file:
            return file.read()

    raise ValueError("Argument 'stream_or_file' is neither a stream nor a file")