8000 Update mypy, use new semantic analyzer (#67) · graphql-python/graphql-core@aa3e89a · GitHub
[go: up one dir, main page]

Skip to content
Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Appearance settings

Commit aa3e89a

Browse files
committed
Update mypy, use new semantic analyzer (#67)
1 parent 07a4cfa commit aa3e89a

27 files changed

+164
-111
lines changed

mypy.ini

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,5 +3,3 @@ python_version = 3.8
33
check_untyped_defs = True
44
warn_redundant_casts = True
55
warn_unused_ignores = True
6-
# https://github.com/python/mypy/issues/7203
7-
new_semantic_analyzer = False

pyproject.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -40,7 +40,7 @@ pytest-describe = ">=0.12"
4040
pyyaml = "^5.1"
4141
black = ">=19.10b0"
4242
flake8 = "^3.7"
43-
mypy = ">=0.720,<0.730"
43+
mypy = ">=0.750,<0.760"
4444
codecov = "^2"
4545
sphinx = "^2.2"
4646
sphinx_rtd_theme = ">=0.4"

src/graphql/execution/execute.py

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -34,7 +34,8 @@
3434
FrozenList,
3535
Path,
3636
)
37-
from ..utilities import get_operation_root_type, type_from_ast
37+
from ..utilities.get_operation_root_type import get_operation_root_type
38+
from ..utilities.type_from_ast import type_from_ast
3839
from ..type import (
3940
GraphQLAbstractType,
4041
GraphQLField,

src/graphql/execution/values.py

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,9 @@
2323
is_input_type,
2424
is_non_null_type,
2525
)
26-
from ..utilities import coerce_input_value, type_from_ast, value_from_ast
26+
from ..utilities.coerce_input_value import coerce_input_value
27+
from ..utilities.type_from_ast import type_from_ast
28+
from ..utilities.value_from_ast import value_from_ast
2729

2830
__all__ = ["get_variable_values", "get_argument_values", "get_directive_values"]
2931

src/graphql/language/ast.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -239,7 +239,7 @@ def __init_subclass__(cls):
239239
keys: List[str] = []
240240
for base in cls.__bases__:
241241
# noinspection PyUnresolvedReferences
242-
keys.extend(base.keys)
242+
keys.extend(base.keys) # type: ignore
243243
keys.extend(cls.__slots__)
244244
cls.keys = keys
245245

src/graphql/language/visitor.py

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
Callable,
66
List,
77
NamedTuple,
8+
Optional,
89
Sequence,
910
Tuple,
1011
Union,
@@ -157,8 +158,11 @@ def __init_subclass__(cls):
157158
for attr, val in cls.__dict__.items():
158159
if attr.startswith("_"):
159160
continue
160-
attr = attr.split("_", 1)
161-
attr, kind = attr if len(attr) > 1 else (attr[0], None)
161+
attr_kind = attr.split("_", 1)
162+
if len(attr_kind) < 2:
163+
kind: Optional[str] = None
164+
else:
165+
attr, kind = attr_kind
162166
if attr in ("enter", "leave"):
163167
if kind:
164168
name = snake_to_camel(kind) + "Node"

src/graphql/subscription/map_async_iterator.py

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
1-
from asyncio import Event, ensure_future, wait
1+
from asyncio import Event, ensure_future, Future, wait
22
from concurrent.futures import FIRST_COMPLETED
33
from inspect import isasyncgen, isawaitable
4-
from typing import AsyncIterable, Callable
4+
from typing import AsyncIterable, Callable, Set
55

66
__all__ = ["MapAsyncIterator"]
77

@@ -42,7 +42,9 @@ async def __anext__(self):
4242
aclose = ensure_future(self._close_event.wait())
4343
anext = ensure_future(self.iterator.__anext__())
4444

45-
done, pending = await wait([aclose, anext], return_when=FIRST_COMPLETED)
45+
pending: Set[Future] = (
46+
await wait([aclose, anext], return_when=FIRST_COMPLETED)
47+
)[1]
4648
for task in pending:
4749
task.cancel()
4850

src/graphql/subscription/subscribe.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -62,7 +62,7 @@ async def subscribe(
6262
if isinstance(result_or_stream, ExecutionResult):
6363
return result_or_stream
6464

65-
async def map_source_to_response(payload):
65+
async def map_source_to_response(payload) -> ExecutionResult:
6666
"""Map source to response.
6767
6868
For each payload yielded from a subscription, map it over the normal GraphQL
@@ -81,7 +81,7 @@ async def map_source_to_response(payload):
8181
operation_name,
8282
field_resolver,
8383
)
84-
return await result if isawaitable(result) else result
84+
return await result if isawaitable(result) else result # type: ignore
8585

8686
return MapAsyncIterator(result_or_stream, map_source_to_response)
8787

src/graphql/type/definition.py

Lines changed: 5 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -361,11 +361,11 @@ def __init__(
361361
" as a sequence of ScalarTypeExtensionNode instances."
362362
)
363363
if serialize is not None:
364-
self.serialize = serialize
364+
self.serialize = serialize # type: ignore
365365
if parse_value is not None:
366-
self.parse_value = parse_value
366+
self.parse_value = parse_value # type: ignore
367367
if parse_literal is not None:
368-
self.parse_literal = parse_literal
368+
self.parse_literal = parse_literal # type: ignore
369369

370370
def __repr__(self):
371371
return f"<{self.__class__.__name__} {self.name!r}>"
@@ -391,9 +391,7 @@ def parse_value(value: Any) -> Any:
391391
"""
392392
return value
393393

394-
def parse_literal( # type: ignore
395-
self, node: ValueNode, _variables: Dict[str, Any] = None
396-
) -> Any:
394+
def parse_literal(self, node: ValueNode, _variables: Dict[str, Any] = None) -> Any:
397395
"""Parses an externally provided literal value to use as an input.
398396
399397
This default method uses the parse_value method and should be replaced
@@ -1247,7 +1245,7 @@ def __init__(
12471245
)
12481246
self._fields = fields
12491247
if out_type is not None:
1250-
self.out_type = out_type
1248+
self.out_type = out_type # type: ignore
12511249

12521250
@staticmethod
12531251
def out_type(value: Dict[str, Any]) -> Any:

src/graphql/type/validate.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -155,7 +155,7 @@ def validate_directives(self):
155155
arg_names: Set[str] = set()
156156
for arg_name, arg in directive.args.items():
157157
# Ensure they are named correctly.
158-
self.validate_name(arg_name, arg)
158+
self.validate_name(arg, arg_name)
159159

160160
# Ensure they are unique per directive.
161161
if arg_name in arg_names:

src/graphql/utilities/coerce_value.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44
from ..language import Node
55
from ..pyutils import Path, inspect, print_path_list
66
from ..type import GraphQLInputType
7-
from . import coerce_input_value
7+
from .coerce_input_value import coerce_input_value
88

99
__all__ = ["coerce_value", "CoercedValue"]
1010

src/graphql/utilities/extend_schema.py

Lines changed: 22 additions & 12 deletions
< 10000 /tr>
Original file line numberDiff line numberDiff line change
@@ -169,8 +169,8 @@ def extend_named_type(type_: GraphQLNamedType) -> GraphQLNamedType:
169169

170170
def extend_directive(directive: GraphQLDirective) -> GraphQLDirective:
171171
kwargs = directive.to_kwargs()
172-
return GraphQLDirective( # type: ignore
173-
**{
172+
return GraphQLDirective(
173+
**{ # type: ignore
174174
**kwargs,
175175
"args": {name: extend_arg(arg) for name, arg in kwargs["args"].items()},
176176
}
@@ -188,8 +188,11 @@ def extend_input_object_type(
188188
**kwargs,
189189
"fields": lambda: {
190190
**{
191-
name: GraphQLInputField( # type: ignore
192-
**{**field.to_kwargs(), "type_": replace_type(field.type)}
191+
name: GraphQLInputField(
192+
**{ # type: ignore
193+
**field.to_kwargs(),
194+
"type_": replace_type(field.type),
195+
}
193196
)
194197
for name, field in kwargs["fields"].items()
195198
},
@@ -306,17 +309,20 @@ def extend_union_type(type_: GraphQLUnionType) -> GraphQLUnionType:
306309
)
307310

308311
def extend_field(field: GraphQLField) -> GraphQLField:
309-
return GraphQLField( # type: ignore
310-
**{
312+
return GraphQLField(
313+
**{ # type: ignore
311314
**field.to_kwargs(),
312315
"type_": replace_type(field.type),
313316
"args": {name: extend_arg(arg) for name, arg in field.args.items()},
314317
}
315318
)
316319

317320
def extend_arg(arg: GraphQLArgument) -> GraphQLArgument:
318-
return GraphQLArgument( # type: ignore
319-
**{**arg.to_kwargs(), "type_": replace_type(arg.type)}
321+
return GraphQLArgument(
322+
**{ # type: ignore
323+
**arg.to_kwargs(),
324+
"type_": replace_type(arg.type),
325+
}
320326
)
321327

322328
# noinspection PyShadowingNames
@@ -358,13 +364,17 @@ def resolve_type(type_name: str) -> GraphQLNamedType:
358364
operation_types[operation] = operation_type.type.name.value
359365

360366
# Then produce and return a Schema with these types.
361-
return GraphQLSchema( # type: ignore
367+
return GraphQLSchema(
362368
# Note: While this could make early assertions to get the correctly
363369
# typed values, that would throw immediately while type system
364370
# validation with validateSchema() will produce more actionable results.
365-
query=get_maybe_type_by_name(operation_types[OperationType.QUERY]),
366-
mutation=get_maybe_type_by_name(operation_types[OperationType.MUTATION]),
367-
subscription=get_maybe_type_by_name(
371+
query=get_maybe_type_by_name( # type: ignore
372+
operation_types[OperationType.QUERY]
373+
),
374+
mutation=get_maybe_type_by_name( # type: ignore
375+
operation_types[OperationType.MUTATION]
376+
),
377+
subscription=get_maybe_type_by_name( # type: ignore
368378
operation_types[OperationType.SUBSCRIPTION]
369379
),
370380
types=list(type_map.values()),

src/graphql/utilities/find_breaking_changes.py

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -89,12 +89,11 @@ def find_breaking_changes(
8989
Given two schemas, returns a list containing descriptions of all the types of
9090
breaking changes covered by the other functions down below.
9191
"""
92-
breaking_changes = [
92+
return [
9393
change
9494
for change in find_schema_changes(old_schema, new_schema)
9595
if isinstance(change.type, BreakingChangeType)
9696
]
97-
return cast(List[BreakingChange], breaking_changes)
9897

9998

10099
def find_dangerous_changes(
@@ -105,12 +104,11 @@ def find_dangerous_changes(
105104
Given two schemas, returns a list containing descriptions of all the types of
106105
potentially dangerous changes covered by the other functions down below.
107106
"""
108-
dangerous_changes = [
107+
return [
109108
change
110109
for change in find_schema_changes(old_schema, new_schema)
111110
if isinstance(change.type, DangerousChangeType)
112111
]
113-
return cast(List[DangerousChange], dangerous_changes)
114112

115113

116114
def find_schema_changes(

src/graphql/utilities/separate_operations.py

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -52,14 +52,15 @@ def separate_operations(document_ast: DocumentNode) -> Dict[str, DocumentNode]:
5252
return separated_document_asts
5353

5454

55+
# noinspection PyAttributeOutsideInit
5556
class SeparateOperations(Visitor):
5657
def __init__(self):
5758
super().__init__()
5859
self.operations: List[OperationDefinitionNode] = []
5960
self.fragments: Dict[str, FragmentDefinitionNode] = {}
6061
self.positions: Dict[ExecutableDefinitionNode, int] = {}
6162
self.dep_graph: DepGraph = defaultdict(set)
62-
self.from_name: str = None
63+
self.from_name: str
6364
self.idx = 0
6465

6566
def enter_operation_definition(self, node, *_args):

tests/execution/test_abstract.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -335,10 +335,10 @@ def resolve_type_on_union_yields_useful_error():
335335
}
336336

337337
def returning_invalid_value_from_resolve_type_yields_useful_error():
338-
foo_interface = GraphQLInterfaceType( # type: ignore
338+
foo_interface = GraphQLInterfaceType(
339339
"FooInterface",
340340
{"bar": GraphQLField(GraphQLString)},
341-
resolve_type=lambda *_args: [],
341+
resolve_type=lambda *_args: [], # type: ignore
342342
)
343343

344344
foo_object = GraphQLObjectType(

tests/execution/test_executor.py

Lines changed: 15 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
import asyncio
2-
from typing import cast
2+
from typing import cast, Awaitable
33

44
from pytest import raises, mark # type: ignore
55

@@ -84,10 +84,10 @@ def pic(self, _info, size=50):
8484
return f"Pic of size: {size}"
8585

8686
def deep(self, _info):
87-
return DeepData() # type: ignore
87+
return DeepData()
8888

8989
def promise(self, _info):
90-
return promise_data() # type: ignore
90+
return promise_data()
9191

9292
# noinspection PyMethodMayBeStatic,PyMethodMayBeStatic
9393
class DeepData:
@@ -134,7 +134,7 @@ async def promise_data():
134134
"a": GraphQLField(GraphQLString),
135135
"b": GraphQLField(GraphQLString),
136136
"c": GraphQLField(GraphQLList(GraphQLString)),
137-
"deeper": GraphQLList(DataType),
137+
"deeper": GraphQLField(GraphQLList(DataType)),
138138
},
139139
)
140140

@@ -170,9 +170,11 @@ async def promise_data():
170170
"""
171171
)
172172

173-
result = await execute(
173+
awaitable_result = execute(
174174
GraphQLSchema(DataType), document, Data(), variable_values={"size": 100}
175175
)
176+
assert isinstance(awaitable_result, Awaitable)
177+
result = await awaitable_result
176178

177179
assert result == (
178180
{
@@ -411,7 +413,9 @@ async def asyncReturnErrorWithExtensions(self, _info):
411413
extensions={"foo": "bar"},
412414
)
413415

414-
result = await execute(schema, document, Data())
416+
awaitable_result = execute(schema, document, Data())
417+
assert isinstance(awaitable_result, Awaitable)
418+
result = await awaitable_result
415419

416420
assert result == (
417421
{
@@ -719,7 +723,9 @@ async def d(self, _info):
719723
def e(self, _info):
720724
return "e"
721725

722-
result = await execute(schema, document, Data())
726+
awaitable_result = execute(schema, document, Data())
727+
assert isinstance(awaitable_result, Awaitable)
728+
result = await awaitable_result
723729

724730
assert result == ({"a": "a", "b": "b", "c": "c", "d": "d", "e": "e"}, None)
725731

@@ -874,13 +880,14 @@ def uses_a_custom_type_resolver():
874880
types=[foo_object],
875881
)
876882

883+
possible_types = None
884+
877885
def type_resolver(_source, info, abstract_type):
878886
# Resolver should be able to figure out all possible types on its own
879887
nonlocal possible_types
880888
possible_types = info.schema.get_possible_types(abstract_type)
881889
return "FooObject"
882890

883-
possible_types = None
884891
root_value = {"foo": {"bar": "bar"}}
885892
result = execute(schema, document, root_value, type_resolver=type_resolver)
886893

0 commit comments

Comments
 (0)
0