Skip to content
This repository was archived by the owner on Sep 3, 2026. It is now read-only.
This repository was archived by the owner on Sep 3, 2026. It is now read-only.

Invalid base class on Protocol (typing_extensions) #296

Description

@autumnjolitz

The following minimal program validates with pytype and mypy

from typing import List

def foo(fh) -> List[bytes]:
    items = []
    for line in iter(fh.readline, b''):
        items.append(line)
    return items


if __name__ == '__main__':
    import io
    test_buffer = io.BytesIO(b'foo\nbar')
    assert foo(test_buffer) == [b'foo\n', b'bar']

The following test program validates with MyPy but faults on pytype with the following messages:

Computing dependencies
Analyzing 1 sources with 0 local dependencies
ninja: Entering directory `/Users/ben/software/horcrux/.pytype'
[1/1] check sample
FAILED: /Users/ben/software/horcrux/.pytype/pyi/sample.pyi
pytype-single --imports_info /Users/ben/software/horcrux/.pytype/imports/sample.imports --module-name sample -V 3.7 -o /Users/ben/software/horcrux/.pytype/pyi/sample.pyi --analyze-annotated --nofail --quick /Users/ben/software/horcrux/sample.py
File "/Users/ben/software/horcrux/sample.py", line 5, in <module>: Invalid base class: <instance of typing_extensions._SpecialForm> [base-class-error]
File "/Users/ben/software/horcrux/sample.py", line 7, in readline: bad option in return type [bad-return-type]
  Expected: bytes
  Actually returned: None
File "/Users/ben/software/horcrux/sample.py", line 20, in <module>: Function foo was called with the wrong arguments [wrong-arg-types]
  Expected: (fh: IReadlineable)
  Actually passed: (fh: io.BytesIO)

For more details, see https://google.github.io/pytype/errors.html.
ninja: build stopped: subcommand failed.
from typing import List
from typing_extensions import Protocol


class IReadlineable(Protocol):
    def readline(self) -> bytes:
        ...


def foo(fh: IReadlineable) -> List[bytes]:
    items = []
    for line in iter(fh.readline, b''):
        items.append(line)
    return items


if __name__ == '__main__':
    import io
    test_buffer = io.BytesIO(b'foo\nbar')
    assert foo(test_buffer) == [b'foo\n', b'bar']

Expected result:

pytype correctly validates Protocol-derived structural subtyping.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

Labels

Type

No type

Projects

No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions