from collections.abc import Iterable, Iterator
from types import TracebackType
from typing import Callable

from _typeshed import StrPath
from typing_extensions import Self

from ._errors import MemoryError, TorfError
from ._torrent import Torrent
from ._utils import File

class TorrentFileStream:
    def __init__(self, torrent: Torrent, content_path: StrPath | None = None) -> None: ...
    def __enter__(self) -> Self: ...
    def __exit__(
        self, exc_type: type[BaseException] | None, exc_value: BaseException | None, traceback: TracebackType | None
    ) -> None: ...
    def close(self) -> None: ...
    @property
    def max_piece_index(self) -> int: ...
    def get_file_position(self, file: File) -> int: ...
    def get_file_at_position(self, position: int, content_path: StrPath | None = None) -> File: ...
    def get_piece_indexes_of_file(self, file: File, exclusive: bool = False) -> list[int]: ...
    def get_files_at_byte_range(
        self, first_byte_index: int, last_byte_index: int, content_path: StrPath | None = None
    ) -> list[File]: ...
    def get_byte_range_of_file(self, file: File) -> tuple[int, int]: ...
    def get_files_at_piece_index(self, piece_index: int, content_path: StrPath | None = None) -> list[File]: ...
    def get_absolute_piece_indexes(self, file: File, relative_piece_indexes: Iterable[int]) -> list[int]: ...
    def get_relative_piece_indexes(self, file: File, relative_piece_indexes: Iterable[int]) -> list[int]: ...
    def get_piece(
        self, piece_index: int, content_path: StrPath | None = None
    ) -> bytes: ...  # Docstrings say it can be `None` but from what I can see it can never be None?

    max_open_files: int = 10
    def iter_pieces(
        self, content_path: StrPath | None = None, oom_callback: Callable[[MemoryError], None] | None = None
    ) -> Iterator[tuple[bytes | None, File, tuple[TorfError, ...]]]: ...
    def get_piece_hash(self, piece_index: int, content_path: StrPath | None = None) -> bytes | None: ...
    def verify_piece(self, piece_index: int, content_path: StrPath | None = None) -> bool | None: ...
