Skip to content

Isinstance checks against Type[SomeProtocol] unexpectedly fails #7932

Closed
@Michael0x2a

Description

@Michael0x2a

Apologies in advance if this is a duplicate issue.

When I try type-checking this program, the final line is inferred to be unreachable. This was a bit surprising to me: I expected to get a "Revealed type is 'SupportsLookup'" note instead.

from typing import Type
from typing_extensions import Protocol

class SupportsLookup(Protocol):
    def lookup(self, key: str) -> int: ...

class Parent: pass

class Child(Parent):
    def lookup(self, key: str) -> int: ...

def cast_and_use(template: Type[SupportsLookup], x: Parent) -> None:
    if isinstance(x, template):
        reveal_type(x)

Somewhat curiously, if I make x be of type object instead of Parent, everything works as expected.

This seems a bit inconsistent to me. Assuming I'm not overlooking some type safety issue in my example, I think it'd be better to always narrow x to SupportsLookup regardless of how it's originally typed as long as the protocol doesn't directly conflict with any signatures defined in Parent.

Note: this issue is a simplification of the root cause of the mypyc error I had in #7917 -- my original version of make_indexing_replay_lookup_func had this issue.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions