-
-
Notifications
You must be signed in to change notification settings - Fork 1.9k
Replace an instance of IO with a protocol #5471
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from 2 commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -2,7 +2,8 @@ import io | |
import sys | ||
from _typeshed import StrPath | ||
from types import TracebackType | ||
from typing import IO, Any, Callable, Dict, Iterable, Iterator, List, Optional, Protocol, Sequence, Tuple, Type, Union | ||
from typing import IO, Any, Callable, Dict, Iterable, Iterator, List, Optional, Protocol, Sequence, Tuple, Type, Union, overload | ||
from typing_extensions import Literal | ||
|
||
_DateTuple = Tuple[int, int, int, int, int, int] | ||
|
||
|
@@ -13,6 +14,16 @@ error = BadZipfile | |
|
||
class LargeZipFile(Exception): ... | ||
|
||
class _ZipStream(Protocol): | ||
def read(self, __n: int) -> bytes: ... | ||
# The following methods are optional: | ||
# def seekable(self) -> bool: ... | ||
# def tell(self) -> int: ... | ||
# def seek(self, __n: int) -> Any: ... | ||
|
||
class _ClosableZipStream(_ZipStream, Protocol): | ||
def close(self) -> Any: ... | ||
|
||
class ZipExtFile(io.BufferedIOBase): | ||
MAX_N: int = ... | ||
MIN_READ_SIZE: int = ... | ||
|
@@ -24,13 +35,53 @@ class ZipExtFile(io.BufferedIOBase): | |
mode: str | ||
name: str | ||
if sys.version_info >= (3, 7): | ||
@overload | ||
def __init__( | ||
self, fileobj: _ClosableZipStream, mode: str, zipinfo: ZipInfo, pwd: Optional[bytes], close_fileobj: Literal[True] | ||
) -> None: ... | ||
@overload | ||
def __init__( | ||
self, fileobj: IO[bytes], mode: str, zipinfo: ZipInfo, pwd: Optional[bytes] = ..., close_fileobj: bool = ... | ||
self, | ||
fileobj: _ClosableZipStream, | ||
mode: str, | ||
zipinfo: ZipInfo, | ||
pwd: Optional[bytes] = ..., | ||
*, | ||
close_fileobj: Literal[True], | ||
) -> None: ... | ||
Akuli marked this conversation as resolved.
Show resolved
Hide resolved
|
||
@overload | ||
def __init__( | ||
self, | ||
fileobj: _ZipStream, | ||
mode: str, | ||
zipinfo: ZipInfo, | ||
pwd: Optional[bytes] = ..., | ||
close_fileobj: bool = ..., | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I don't think this works as intended. If There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. See above: I think this is a reasonable tradeoff, considering our "prefer false negatives over false positives" policy. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Then we might as well get rid of There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. But having it separate has the advantage that the following fails: ZipExtFile(my_non_closable_stream, close_fileobj=True) The only thing that can't be checked properly is the following: close: bool = True
ZipExtFile(my_non_closable_stream, close_fileobj=close) There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I don't think that fails. It doesn't match the first two overloads, but it does match the third overload which just requires any stream, and There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Good point. At this point I think that maybe the first solution was the best, and until python/mypy#6113 is fixed, people just use There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Since we prefer false negatives, it might be better to just never require a |
||
) -> None: ... | ||
else: | ||
@overload | ||
def __init__( | ||
self, | ||
fileobj: _ClosableZipStream, | ||
mode: str, | ||
zipinfo: ZipInfo, | ||
decrypter: Optional[Callable[[Sequence[int]], bytes]], | ||
close_fileobj: Literal[True], | ||
) -> None: ... | ||
@overload | ||
def __init__( | ||
self, | ||
fileobj: _ClosableZipStream, | ||
mode: str, | ||
zipinfo: ZipInfo, | ||
decrypter: Optional[Callable[[Sequence[int]], bytes]] = ..., | ||
*, | ||
close_fileobj: Literal[True], | ||
) -> None: ... | ||
@overload | ||
def __init__( | ||
self, | ||
fileobj: IO[bytes], | ||
fileobj: _ZipStream, | ||
mode: str, | ||
zipinfo: ZipInfo, | ||
decrypter: Optional[Callable[[Sequence[int]], bytes]] = ..., | ||
|
Uh oh!
There was an error while loading. Please reload this page.