Skip to content

Fix mypy issue with name and fullname being properties #1

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

Merged
merged 1 commit into from
Apr 24, 2020
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
29 changes: 23 additions & 6 deletions fastenum/mypy_plugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -124,7 +124,7 @@ def _define_method(
for arg in arguments:
assert arg.type_annotation, 'All arguments must be fully typed.'
arg_types.append(arg.type_annotation)
arg_names.append(arg.variable.name())
arg_names.append(get_name(arg.variable))
arg_kinds.append(arg.kind)

# Creating type of a callable, this is equialent to writing
Expand Down Expand Up @@ -229,7 +229,7 @@ def transform_enum_class_def(context: mypy.plugin.ClassDefContext) -> None:
# To get over that we remove `int` base class from that class def.
info.bases = [
base for base in info.bases
if base.type.fullname() != 'builtins.int'
if get_fullname(base.type) != 'builtins.int'
]

# First clear all `nodes.AssignmentStmt` in class.
Expand Down Expand Up @@ -272,7 +272,7 @@ def transform_enum_class_def(context: mypy.plugin.ClassDefContext) -> None:
# it should return itself.
# So as a hotfix we redefine these methods on our inherited enum class
# to have more specific typing (which is still not violating original metaclass typing)
_define_method(context, metaclass_type.type, metaclass_type.type.fullname(), '__next__', [], self_type)
_define_method(context, metaclass_type.type, get_fullname(metaclass_type.type), '__next__', [], self_type)

# Example how these all lines below would look like in Python:
#
Expand All @@ -284,7 +284,7 @@ def transform_enum_class_def(context: mypy.plugin.ClassDefContext) -> None:
_define_method(
context,
metaclass_type.type,
metaclass_type.type.fullname(),
get_fullname(metaclass_type.type),
'__getitem__',
[
nodes.Argument(nodes.Var('cls', self_type), self_type, None, nodes.ARG_POS),
Expand Down Expand Up @@ -459,15 +459,15 @@ def transform_enum_type(context: mypy.plugin.AnalyzeTypeContext) -> types.Type:
meta_enum_instance = types.Instance(meta_info, [])
self_tvar_expr = nodes.TypeVarExpr(
'_EnumMetaType',
f'{meta_info.fullname()}._EnumMetaType',
f'{get_fullname(meta_info)}._EnumMetaType',
[],
meta_enum_instance
)
meta_info.names['_EnumMetaType'] = nodes.SymbolTableNode(nodes.MDEF, self_tvar_expr)

self_tvar_def = types.TypeVarDef(
'_EnumMetaType',
f'{meta_info.fullname()}._EnumMetaType',
f'{get_fullname(meta_info)}._EnumMetaType',
-1,
[],
meta_enum_instance
Expand Down Expand Up @@ -594,3 +594,20 @@ def plugin(_: str) -> Type[FastEnumPlugin]:
# The first argument (mypy version) can be used to have multiple versions of this
# plugin for multiple mypy versions.
return FastEnumPlugin


# Taken and modified from https://github.com/samuelcolvin/pydantic/pull/1058/files#diff-ef0fe5e1687ec75a3d9fe2d593799ff8R669
def get_fullname(x: Union[nodes.FuncBase, nodes.SymbolNode]) -> str:
'''
Used for compatibility with mypy 0.740; can be dropped once support for 0.740 is dropped.
'''
fn = x.fullname
return fn() if callable(fn) else fn


def get_name(x: Union[nodes.FuncBase, nodes.SymbolNode]) -> str:
'''
Used for compatibility with mypy 0.740; can be dropped once support for 0.740 is dropped.
'''
fn = x.fullname
return fn() if callable(fn) else fn