strawberry-graphql 0.283.0__py3-none-any.whl → 0.284.3__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of strawberry-graphql might be problematic. Click here for more details.
- strawberry/aiohttp/test/client.py +8 -15
- strawberry/aiohttp/views.py +12 -15
- strawberry/annotation.py +19 -23
- strawberry/asgi/__init__.py +18 -17
- strawberry/asgi/test/client.py +6 -6
- strawberry/chalice/views.py +6 -6
- strawberry/channels/handlers/base.py +7 -8
- strawberry/channels/handlers/http_handler.py +18 -20
- strawberry/channels/handlers/ws_handler.py +10 -12
- strawberry/channels/router.py +3 -4
- strawberry/channels/testing.py +7 -9
- strawberry/cli/commands/codegen.py +7 -7
- strawberry/cli/commands/schema_codegen.py +1 -2
- strawberry/cli/commands/upgrade/__init__.py +1 -3
- strawberry/cli/commands/upgrade/_run_codemod.py +2 -2
- strawberry/codegen/plugins/print_operation.py +2 -2
- strawberry/codegen/plugins/python.py +2 -2
- strawberry/codegen/query_codegen.py +20 -30
- strawberry/codegen/types.py +32 -32
- strawberry/codemods/annotated_unions.py +2 -2
- strawberry/dataloader.py +28 -24
- strawberry/directive.py +6 -7
- strawberry/django/test/client.py +3 -3
- strawberry/django/views.py +16 -19
- strawberry/exceptions/__init__.py +4 -4
- strawberry/exceptions/conflicting_arguments.py +2 -2
- strawberry/exceptions/duplicated_type_name.py +4 -4
- strawberry/exceptions/exception.py +3 -3
- strawberry/exceptions/handler.py +8 -7
- strawberry/exceptions/invalid_argument_type.py +2 -2
- strawberry/exceptions/invalid_superclass_interface.py +2 -2
- strawberry/exceptions/invalid_union_type.py +4 -4
- strawberry/exceptions/missing_arguments_annotations.py +2 -2
- strawberry/exceptions/missing_dependencies.py +2 -4
- strawberry/exceptions/missing_field_annotation.py +2 -2
- strawberry/exceptions/missing_return_annotation.py +2 -2
- strawberry/exceptions/object_is_not_a_class.py +2 -2
- strawberry/exceptions/object_is_not_an_enum.py +2 -2
- strawberry/exceptions/permission_fail_silently_requires_optional.py +2 -2
- strawberry/exceptions/private_strawberry_field.py +2 -2
- strawberry/exceptions/scalar_already_registered.py +2 -2
- strawberry/exceptions/syntax.py +3 -3
- strawberry/exceptions/unresolved_field_type.py +2 -2
- strawberry/exceptions/utils/source_finder.py +25 -25
- strawberry/experimental/pydantic/_compat.py +8 -7
- strawberry/experimental/pydantic/conversion.py +2 -2
- strawberry/experimental/pydantic/conversion_types.py +2 -2
- strawberry/experimental/pydantic/error_type.py +10 -12
- strawberry/experimental/pydantic/fields.py +9 -15
- strawberry/experimental/pydantic/object_type.py +15 -23
- strawberry/experimental/pydantic/utils.py +1 -2
- strawberry/ext/mypy_plugin.py +12 -14
- strawberry/extensions/base_extension.py +2 -1
- strawberry/extensions/context.py +13 -18
- strawberry/extensions/directives.py +3 -1
- strawberry/extensions/field_extension.py +4 -4
- strawberry/extensions/max_aliases.py +1 -3
- strawberry/extensions/parser_cache.py +1 -2
- strawberry/extensions/query_depth_limiter.py +18 -14
- strawberry/extensions/runner.py +2 -2
- strawberry/extensions/tracing/apollo.py +3 -3
- strawberry/extensions/tracing/datadog.py +3 -3
- strawberry/extensions/tracing/opentelemetry.py +6 -8
- strawberry/extensions/tracing/utils.py +3 -1
- strawberry/extensions/utils.py +2 -2
- strawberry/extensions/validation_cache.py +1 -2
- strawberry/fastapi/context.py +6 -6
- strawberry/fastapi/router.py +33 -36
- strawberry/federation/argument.py +4 -5
- strawberry/federation/enum.py +18 -21
- strawberry/federation/field.py +94 -97
- strawberry/federation/object_type.py +56 -58
- strawberry/federation/scalar.py +27 -35
- strawberry/federation/schema.py +15 -16
- strawberry/federation/schema_directive.py +7 -6
- strawberry/federation/schema_directives.py +11 -11
- strawberry/federation/union.py +4 -4
- strawberry/flask/views.py +10 -11
- strawberry/http/__init__.py +14 -14
- strawberry/http/async_base_view.py +23 -28
- strawberry/http/base.py +11 -12
- strawberry/http/ides.py +2 -3
- strawberry/http/sync_base_view.py +11 -13
- strawberry/http/types.py +3 -3
- strawberry/litestar/controller.py +40 -35
- strawberry/permission.py +4 -6
- strawberry/printer/ast_from_value.py +3 -5
- strawberry/printer/printer.py +8 -13
- strawberry/quart/views.py +12 -14
- strawberry/relay/exceptions.py +4 -4
- strawberry/relay/fields.py +33 -32
- strawberry/relay/types.py +31 -34
- strawberry/relay/utils.py +2 -2
- strawberry/resolvers.py +2 -1
- strawberry/sanic/context.py +1 -0
- strawberry/sanic/utils.py +3 -3
- strawberry/sanic/views.py +11 -14
- strawberry/scalars.py +2 -2
- strawberry/schema/_graphql_core.py +5 -5
- strawberry/schema/base.py +32 -33
- strawberry/schema/compat.py +9 -9
- strawberry/schema/config.py +5 -2
- strawberry/schema/exceptions.py +1 -3
- strawberry/schema/name_converter.py +6 -6
- strawberry/schema/schema.py +55 -60
- strawberry/schema/schema_converter.py +27 -22
- strawberry/schema/types/base_scalars.py +1 -1
- strawberry/schema/types/concrete_type.py +5 -5
- strawberry/schema_codegen/__init__.py +3 -3
- strawberry/schema_directive.py +7 -6
- strawberry/subscriptions/protocols/graphql_transport_ws/handlers.py +5 -6
- strawberry/subscriptions/protocols/graphql_transport_ws/types.py +20 -20
- strawberry/subscriptions/protocols/graphql_ws/handlers.py +5 -6
- strawberry/subscriptions/protocols/graphql_ws/types.py +14 -14
- strawberry/test/client.py +18 -18
- strawberry/tools/create_type.py +2 -3
- strawberry/types/arguments.py +25 -26
- strawberry/types/auto.py +3 -4
- strawberry/types/base.py +25 -27
- strawberry/types/enum.py +22 -25
- strawberry/types/execution.py +14 -15
- strawberry/types/field.py +108 -108
- strawberry/types/fields/resolver.py +19 -21
- strawberry/types/info.py +5 -11
- strawberry/types/lazy_type.py +2 -3
- strawberry/types/maybe.py +12 -3
- strawberry/types/mutation.py +115 -118
- strawberry/types/nodes.py +2 -2
- strawberry/types/object_type.py +43 -63
- strawberry/types/scalar.py +37 -43
- strawberry/types/union.py +12 -14
- strawberry/utils/aio.py +12 -9
- strawberry/utils/await_maybe.py +3 -3
- strawberry/utils/deprecations.py +2 -2
- strawberry/utils/importer.py +1 -2
- strawberry/utils/inspect.py +4 -6
- strawberry/utils/logging.py +2 -2
- strawberry/utils/operation.py +4 -4
- strawberry/utils/typing.py +18 -83
- {strawberry_graphql-0.283.0.dist-info → strawberry_graphql-0.284.3.dist-info}/METADATA +2 -2
- strawberry_graphql-0.284.3.dist-info/RECORD +243 -0
- strawberry/utils/dataclasses.py +0 -37
- strawberry_graphql-0.283.0.dist-info/RECORD +0 -244
- {strawberry_graphql-0.283.0.dist-info → strawberry_graphql-0.284.3.dist-info}/WHEEL +0 -0
- {strawberry_graphql-0.283.0.dist-info → strawberry_graphql-0.284.3.dist-info}/entry_points.txt +0 -0
- {strawberry_graphql-0.283.0.dist-info → strawberry_graphql-0.284.3.dist-info}/licenses/LICENSE +0 -0
|
@@ -5,11 +5,9 @@ import datetime
|
|
|
5
5
|
import json
|
|
6
6
|
from typing import (
|
|
7
7
|
TYPE_CHECKING,
|
|
8
|
-
Optional,
|
|
9
8
|
TypedDict,
|
|
10
|
-
|
|
9
|
+
TypeGuard,
|
|
11
10
|
)
|
|
12
|
-
from typing_extensions import TypeGuard
|
|
13
11
|
|
|
14
12
|
from strawberry.http.async_base_view import AsyncBaseHTTPView, AsyncWebSocketAdapter
|
|
15
13
|
from strawberry.http.exceptions import NonJsonMessageReceived, NonTextMessageReceived
|
|
@@ -62,7 +60,7 @@ class ChannelsWebSocketAdapter(AsyncWebSocketAdapter):
|
|
|
62
60
|
|
|
63
61
|
|
|
64
62
|
class MessageQueueData(TypedDict):
|
|
65
|
-
message:
|
|
63
|
+
message: str | None
|
|
66
64
|
disconnected: bool
|
|
67
65
|
|
|
68
66
|
|
|
@@ -102,7 +100,7 @@ class GraphQLWSConsumer(
|
|
|
102
100
|
```
|
|
103
101
|
"""
|
|
104
102
|
|
|
105
|
-
websocket_adapter_class = ChannelsWebSocketAdapter
|
|
103
|
+
websocket_adapter_class = ChannelsWebSocketAdapter # type: ignore
|
|
106
104
|
|
|
107
105
|
def __init__(
|
|
108
106
|
self,
|
|
@@ -113,7 +111,7 @@ class GraphQLWSConsumer(
|
|
|
113
111
|
GRAPHQL_TRANSPORT_WS_PROTOCOL,
|
|
114
112
|
GRAPHQL_WS_PROTOCOL,
|
|
115
113
|
),
|
|
116
|
-
connection_init_wait_timeout:
|
|
114
|
+
connection_init_wait_timeout: datetime.timedelta | None = None,
|
|
117
115
|
) -> None:
|
|
118
116
|
if connection_init_wait_timeout is None:
|
|
119
117
|
connection_init_wait_timeout = datetime.timedelta(minutes=1)
|
|
@@ -123,7 +121,7 @@ class GraphQLWSConsumer(
|
|
|
123
121
|
self.keep_alive_interval = keep_alive_interval
|
|
124
122
|
self.protocols = subscription_protocols
|
|
125
123
|
self.message_queue: asyncio.Queue[MessageQueueData] = asyncio.Queue()
|
|
126
|
-
self.run_task:
|
|
124
|
+
self.run_task: asyncio.Task | None = None
|
|
127
125
|
|
|
128
126
|
super().__init__()
|
|
129
127
|
|
|
@@ -131,7 +129,7 @@ class GraphQLWSConsumer(
|
|
|
131
129
|
self.run_task = asyncio.create_task(self.run(self))
|
|
132
130
|
|
|
133
131
|
async def receive(
|
|
134
|
-
self, text_data:
|
|
132
|
+
self, text_data: str | None = None, bytes_data: bytes | None = None
|
|
135
133
|
) -> None:
|
|
136
134
|
if text_data:
|
|
137
135
|
self.message_queue.put_nowait({"message": text_data, "disconnected": False})
|
|
@@ -143,7 +141,7 @@ class GraphQLWSConsumer(
|
|
|
143
141
|
assert self.run_task
|
|
144
142
|
await self.run_task
|
|
145
143
|
|
|
146
|
-
async def get_root_value(self, request: GraphQLWSConsumer) ->
|
|
144
|
+
async def get_root_value(self, request: GraphQLWSConsumer) -> RootValue | None:
|
|
147
145
|
return None
|
|
148
146
|
|
|
149
147
|
async def get_context(
|
|
@@ -163,7 +161,7 @@ class GraphQLWSConsumer(
|
|
|
163
161
|
|
|
164
162
|
def create_response(
|
|
165
163
|
self,
|
|
166
|
-
response_data:
|
|
164
|
+
response_data: GraphQLHTTPResponse | list[GraphQLHTTPResponse],
|
|
167
165
|
sub_response: GraphQLWSConsumer,
|
|
168
166
|
) -> GraphQLWSConsumer:
|
|
169
167
|
raise NotImplementedError
|
|
@@ -178,14 +176,14 @@ class GraphQLWSConsumer(
|
|
|
178
176
|
|
|
179
177
|
async def pick_websocket_subprotocol(
|
|
180
178
|
self, request: GraphQLWSConsumer
|
|
181
|
-
) ->
|
|
179
|
+
) -> str | None:
|
|
182
180
|
protocols = request.scope["subprotocols"]
|
|
183
181
|
intersection = set(protocols) & set(self.protocols)
|
|
184
182
|
sorted_intersection = sorted(intersection, key=protocols.index)
|
|
185
183
|
return next(iter(sorted_intersection), None)
|
|
186
184
|
|
|
187
185
|
async def create_websocket_response(
|
|
188
|
-
self, request: GraphQLWSConsumer, subprotocol:
|
|
186
|
+
self, request: GraphQLWSConsumer, subprotocol: str | None
|
|
189
187
|
) -> GraphQLWSConsumer:
|
|
190
188
|
await request.accept(subprotocol=subprotocol)
|
|
191
189
|
return request
|
strawberry/channels/router.py
CHANGED
|
@@ -7,11 +7,10 @@ on preferences and client support. Then it hands off to the appropriate consumer
|
|
|
7
7
|
|
|
8
8
|
from __future__ import annotations
|
|
9
9
|
|
|
10
|
-
from typing import TYPE_CHECKING
|
|
11
|
-
|
|
12
|
-
from django.urls import re_path
|
|
10
|
+
from typing import TYPE_CHECKING
|
|
13
11
|
|
|
14
12
|
from channels.routing import ProtocolTypeRouter, URLRouter
|
|
13
|
+
from django.urls import re_path
|
|
15
14
|
|
|
16
15
|
from .handlers.http_handler import GraphQLHTTPConsumer
|
|
17
16
|
from .handlers.ws_handler import GraphQLWSConsumer
|
|
@@ -47,7 +46,7 @@ class GraphQLProtocolTypeRouter(ProtocolTypeRouter):
|
|
|
47
46
|
def __init__(
|
|
48
47
|
self,
|
|
49
48
|
schema: BaseSchema,
|
|
50
|
-
django_application:
|
|
49
|
+
django_application: str | None = None,
|
|
51
50
|
url_pattern: str = "^graphql",
|
|
52
51
|
) -> None:
|
|
53
52
|
http_urls = [re_path(url_pattern, GraphQLHTTPConsumer.as_asgi(schema=schema))]
|
strawberry/channels/testing.py
CHANGED
|
@@ -4,13 +4,11 @@ import uuid
|
|
|
4
4
|
from typing import (
|
|
5
5
|
TYPE_CHECKING,
|
|
6
6
|
Any,
|
|
7
|
-
Optional,
|
|
8
|
-
Union,
|
|
9
7
|
)
|
|
10
8
|
|
|
9
|
+
from channels.testing.websocket import WebsocketCommunicator
|
|
11
10
|
from graphql import GraphQLError, GraphQLFormattedError
|
|
12
11
|
|
|
13
|
-
from channels.testing.websocket import WebsocketCommunicator
|
|
14
12
|
from strawberry.subscriptions import GRAPHQL_TRANSPORT_WS_PROTOCOL, GRAPHQL_WS_PROTOCOL
|
|
15
13
|
from strawberry.subscriptions.protocols.graphql_transport_ws import (
|
|
16
14
|
types as transport_ws_types,
|
|
@@ -53,7 +51,7 @@ class GraphQLWebsocketCommunicator(WebsocketCommunicator):
|
|
|
53
51
|
self,
|
|
54
52
|
application: ASGIApplication,
|
|
55
53
|
path: str,
|
|
56
|
-
headers:
|
|
54
|
+
headers: list[tuple[bytes, bytes]] | None = None,
|
|
57
55
|
protocol: str = GRAPHQL_TRANSPORT_WS_PROTOCOL,
|
|
58
56
|
connection_params: dict | None = None,
|
|
59
57
|
**kwargs: Any,
|
|
@@ -83,9 +81,9 @@ class GraphQLWebsocketCommunicator(WebsocketCommunicator):
|
|
|
83
81
|
|
|
84
82
|
async def __aexit__(
|
|
85
83
|
self,
|
|
86
|
-
exc_type:
|
|
87
|
-
exc_val:
|
|
88
|
-
exc_tb:
|
|
84
|
+
exc_type: type[BaseException] | None,
|
|
85
|
+
exc_val: BaseException | None,
|
|
86
|
+
exc_tb: TracebackType | None,
|
|
89
87
|
) -> None:
|
|
90
88
|
await self.disconnect()
|
|
91
89
|
|
|
@@ -114,8 +112,8 @@ class GraphQLWebsocketCommunicator(WebsocketCommunicator):
|
|
|
114
112
|
# get transformed into `FormattedExecutionResult` on the wire, but we attempt
|
|
115
113
|
# to do a limited representation of them here, to make testing simpler.
|
|
116
114
|
async def subscribe(
|
|
117
|
-
self, query: str, variables:
|
|
118
|
-
) ->
|
|
115
|
+
self, query: str, variables: dict | None = None
|
|
116
|
+
) -> ExecutionResult | AsyncIterator[ExecutionResult]:
|
|
119
117
|
id_ = uuid.uuid4().hex
|
|
120
118
|
|
|
121
119
|
if self.protocol == GRAPHQL_TRANSPORT_WS_PROTOCOL:
|
|
@@ -4,7 +4,7 @@ import functools
|
|
|
4
4
|
import importlib
|
|
5
5
|
import inspect
|
|
6
6
|
from pathlib import Path # noqa: TC003
|
|
7
|
-
from typing import
|
|
7
|
+
from typing import cast
|
|
8
8
|
|
|
9
9
|
import rich
|
|
10
10
|
import typer
|
|
@@ -22,9 +22,9 @@ def _is_codegen_plugin(obj: object) -> bool:
|
|
|
22
22
|
)
|
|
23
23
|
|
|
24
24
|
|
|
25
|
-
def _import_plugin(plugin: str) ->
|
|
25
|
+
def _import_plugin(plugin: str) -> type[QueryCodegenPlugin] | None:
|
|
26
26
|
module_name = plugin
|
|
27
|
-
symbol_name:
|
|
27
|
+
symbol_name: str | None = None
|
|
28
28
|
|
|
29
29
|
if ":" in plugin:
|
|
30
30
|
module_name, symbol_name = plugin.split(":", 1)
|
|
@@ -61,7 +61,7 @@ def _import_plugin(plugin: str) -> Optional[type[QueryCodegenPlugin]]:
|
|
|
61
61
|
@functools.lru_cache
|
|
62
62
|
def _load_plugin(
|
|
63
63
|
plugin_path: str,
|
|
64
|
-
) -> type[
|
|
64
|
+
) -> type[QueryCodegenPlugin | ConsolePlugin]:
|
|
65
65
|
# try to import plugin_name from current folder
|
|
66
66
|
# then try to import from strawberry.codegen.plugins
|
|
67
67
|
|
|
@@ -79,7 +79,7 @@ def _load_plugin(
|
|
|
79
79
|
|
|
80
80
|
def _load_plugins(
|
|
81
81
|
plugin_ids: list[str], query: Path
|
|
82
|
-
) -> list[
|
|
82
|
+
) -> list[QueryCodegenPlugin | ConsolePlugin]:
|
|
83
83
|
plugins = []
|
|
84
84
|
for ptype_id in plugin_ids:
|
|
85
85
|
ptype = _load_plugin(ptype_id)
|
|
@@ -91,7 +91,7 @@ def _load_plugins(
|
|
|
91
91
|
|
|
92
92
|
@app.command(help="Generate code from a query")
|
|
93
93
|
def codegen(
|
|
94
|
-
query:
|
|
94
|
+
query: list[Path] | None = typer.Argument(
|
|
95
95
|
default=None, exists=True, dir_okay=False
|
|
96
96
|
),
|
|
97
97
|
schema: str = typer.Option(..., help="Python path to the schema file"),
|
|
@@ -120,7 +120,7 @@ def codegen(
|
|
|
120
120
|
"-p",
|
|
121
121
|
"--plugins",
|
|
122
122
|
),
|
|
123
|
-
cli_plugin:
|
|
123
|
+
cli_plugin: str | None = None,
|
|
124
124
|
) -> None:
|
|
125
125
|
if not query:
|
|
126
126
|
return
|
|
@@ -1,5 +1,4 @@
|
|
|
1
1
|
from pathlib import Path
|
|
2
|
-
from typing import Optional
|
|
3
2
|
|
|
4
3
|
import typer
|
|
5
4
|
|
|
@@ -10,7 +9,7 @@ from strawberry.schema_codegen import codegen
|
|
|
10
9
|
@app.command(help="Generate code from a query")
|
|
11
10
|
def schema_codegen(
|
|
12
11
|
schema: Path = typer.Argument(exists=True),
|
|
13
|
-
output:
|
|
12
|
+
output: Path | None = typer.Option(
|
|
14
13
|
None,
|
|
15
14
|
"-o",
|
|
16
15
|
"--output",
|
|
@@ -47,8 +47,6 @@ def upgrade(
|
|
|
47
47
|
|
|
48
48
|
raise typer.Exit(2)
|
|
49
49
|
|
|
50
|
-
python_target_version = tuple(int(x) for x in python_target.split("."))
|
|
51
|
-
|
|
52
50
|
transformer: ConvertUnionToAnnotatedUnion | UpdateImportsCodemod
|
|
53
51
|
|
|
54
52
|
if codemod == "update-imports":
|
|
@@ -57,7 +55,7 @@ def upgrade(
|
|
|
57
55
|
else:
|
|
58
56
|
transformer = ConvertUnionToAnnotatedUnion(
|
|
59
57
|
CodemodContext(),
|
|
60
|
-
use_pipe_syntax=
|
|
58
|
+
use_pipe_syntax=True,
|
|
61
59
|
use_typing_extensions=use_typing_extensions,
|
|
62
60
|
)
|
|
63
61
|
|
|
@@ -4,7 +4,7 @@ import contextlib
|
|
|
4
4
|
import os
|
|
5
5
|
from importlib.metadata import version
|
|
6
6
|
from multiprocessing import Pool, cpu_count
|
|
7
|
-
from typing import TYPE_CHECKING, Any,
|
|
7
|
+
from typing import TYPE_CHECKING, Any, TypeAlias
|
|
8
8
|
|
|
9
9
|
from libcst.codemod._cli import ExecutionConfig, ExecutionResult, _execute_transform
|
|
10
10
|
from rich.progress import Progress
|
|
@@ -16,7 +16,7 @@ if TYPE_CHECKING:
|
|
|
16
16
|
|
|
17
17
|
from libcst.codemod import Codemod
|
|
18
18
|
|
|
19
|
-
ProgressType =
|
|
19
|
+
ProgressType: TypeAlias = type[Progress] | type[FakeProgress]
|
|
20
20
|
|
|
21
21
|
|
|
22
22
|
def _get_libcst_version() -> tuple[int, int, int]:
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
from __future__ import annotations
|
|
2
2
|
|
|
3
3
|
import textwrap
|
|
4
|
-
from typing import TYPE_CHECKING
|
|
4
|
+
from typing import TYPE_CHECKING
|
|
5
5
|
|
|
6
6
|
from strawberry.codegen import CodegenFile, QueryCodegenPlugin
|
|
7
7
|
from strawberry.codegen.types import (
|
|
@@ -93,7 +93,7 @@ class PrintOperationPlugin(QueryCodegenPlugin):
|
|
|
93
93
|
return f"({variables})"
|
|
94
94
|
|
|
95
95
|
def _print_graphql_type(
|
|
96
|
-
self, type: GraphQLType, parent_type:
|
|
96
|
+
self, type: GraphQLType, parent_type: GraphQLType | None = None
|
|
97
97
|
) -> str:
|
|
98
98
|
if isinstance(type, GraphQLOptional):
|
|
99
99
|
return self._print_graphql_type(type.of_type, type)
|
|
@@ -3,7 +3,7 @@ from __future__ import annotations
|
|
|
3
3
|
import textwrap
|
|
4
4
|
from collections import defaultdict
|
|
5
5
|
from dataclasses import dataclass
|
|
6
|
-
from typing import TYPE_CHECKING, ClassVar
|
|
6
|
+
from typing import TYPE_CHECKING, ClassVar
|
|
7
7
|
|
|
8
8
|
from strawberry.codegen import CodegenFile, QueryCodegenPlugin
|
|
9
9
|
from strawberry.codegen.types import (
|
|
@@ -31,7 +31,7 @@ if TYPE_CHECKING:
|
|
|
31
31
|
@dataclass
|
|
32
32
|
class PythonType:
|
|
33
33
|
type: str
|
|
34
|
-
module:
|
|
34
|
+
module: str | None = None
|
|
35
35
|
|
|
36
36
|
|
|
37
37
|
class PythonPlugin(QueryCodegenPlugin):
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
from __future__ import annotations
|
|
2
2
|
|
|
3
|
-
from collections.abc import Iterable, Mapping, Sequence
|
|
3
|
+
from collections.abc import Callable, Iterable, Mapping, Sequence
|
|
4
4
|
from dataclasses import MISSING, dataclass
|
|
5
5
|
from enum import Enum
|
|
6
6
|
from functools import cmp_to_key, partial
|
|
@@ -8,12 +8,9 @@ from pathlib import Path
|
|
|
8
8
|
from typing import (
|
|
9
9
|
TYPE_CHECKING,
|
|
10
10
|
Any,
|
|
11
|
-
Callable,
|
|
12
|
-
Optional,
|
|
13
|
-
Union,
|
|
14
11
|
cast,
|
|
15
12
|
)
|
|
16
|
-
from typing_extensions import
|
|
13
|
+
from typing_extensions import Protocol
|
|
17
14
|
|
|
18
15
|
import rich
|
|
19
16
|
from graphql import (
|
|
@@ -122,7 +119,7 @@ class CodegenResult:
|
|
|
122
119
|
|
|
123
120
|
|
|
124
121
|
class HasSelectionSet(Protocol):
|
|
125
|
-
selection_set:
|
|
122
|
+
selection_set: SelectionSetNode | None
|
|
126
123
|
|
|
127
124
|
|
|
128
125
|
class QueryCodegenPlugin:
|
|
@@ -234,7 +231,7 @@ class QueryCodegenPluginManager:
|
|
|
234
231
|
def __init__(
|
|
235
232
|
self,
|
|
236
233
|
plugins: list[QueryCodegenPlugin],
|
|
237
|
-
console_plugin:
|
|
234
|
+
console_plugin: ConsolePlugin | None = None,
|
|
238
235
|
) -> None:
|
|
239
236
|
self.plugins = plugins
|
|
240
237
|
self.console_plugin = console_plugin
|
|
@@ -298,7 +295,7 @@ class QueryCodegen:
|
|
|
298
295
|
self,
|
|
299
296
|
schema: Schema,
|
|
300
297
|
plugins: list[QueryCodegenPlugin],
|
|
301
|
-
console_plugin:
|
|
298
|
+
console_plugin: ConsolePlugin | None = None,
|
|
302
299
|
) -> None:
|
|
303
300
|
self.schema = schema
|
|
304
301
|
self.plugin_manager = QueryCodegenPluginManager(plugins, console_plugin)
|
|
@@ -390,7 +387,7 @@ class QueryCodegen:
|
|
|
390
387
|
raise ValueError(f"Unsupported type: {type(selection)}") # pragma: no cover
|
|
391
388
|
|
|
392
389
|
def _convert_selection_set(
|
|
393
|
-
self, selection_set:
|
|
390
|
+
self, selection_set: SelectionSetNode | None
|
|
394
391
|
) -> list[GraphQLSelection]:
|
|
395
392
|
if selection_set is None:
|
|
396
393
|
return []
|
|
@@ -473,18 +470,13 @@ class QueryCodegen:
|
|
|
473
470
|
class_name=result_class_name,
|
|
474
471
|
)
|
|
475
472
|
|
|
476
|
-
operation_kind = cast(
|
|
477
|
-
"Literal['query', 'mutation', 'subscription']",
|
|
478
|
-
operation_definition.operation.value,
|
|
479
|
-
)
|
|
480
|
-
|
|
481
473
|
variables, variables_type = self._convert_variable_definitions(
|
|
482
474
|
operation_definition.variable_definitions, operation_name=operation_name
|
|
483
475
|
)
|
|
484
476
|
|
|
485
477
|
return GraphQLOperation(
|
|
486
478
|
operation_definition.name.value,
|
|
487
|
-
kind=
|
|
479
|
+
kind=operation_definition.operation.value,
|
|
488
480
|
selections=self._convert_selection_set(operation_definition.selection_set),
|
|
489
481
|
directives=self._convert_directives(operation_definition.directives),
|
|
490
482
|
variables=variables,
|
|
@@ -494,9 +486,9 @@ class QueryCodegen:
|
|
|
494
486
|
|
|
495
487
|
def _convert_variable_definitions(
|
|
496
488
|
self,
|
|
497
|
-
variable_definitions:
|
|
489
|
+
variable_definitions: Iterable[VariableDefinitionNode] | None,
|
|
498
490
|
operation_name: str,
|
|
499
|
-
) -> tuple[list[GraphQLVariable],
|
|
491
|
+
) -> tuple[list[GraphQLVariable], GraphQLObjectType | None]:
|
|
500
492
|
if not variable_definitions:
|
|
501
493
|
return [], None
|
|
502
494
|
|
|
@@ -527,7 +519,7 @@ class QueryCodegen:
|
|
|
527
519
|
|
|
528
520
|
def _get_field_type(
|
|
529
521
|
self,
|
|
530
|
-
field_type:
|
|
522
|
+
field_type: StrawberryType | type,
|
|
531
523
|
) -> GraphQLType:
|
|
532
524
|
if isinstance(field_type, StrawberryOptional):
|
|
533
525
|
return GraphQLOptional(self._get_field_type(field_type.of_type))
|
|
@@ -557,7 +549,7 @@ class QueryCodegen:
|
|
|
557
549
|
raise ValueError(f"Unsupported type: {field_type}") # pragma: no cover
|
|
558
550
|
|
|
559
551
|
def _collect_type_from_strawberry_type(
|
|
560
|
-
self, strawberry_type:
|
|
552
|
+
self, strawberry_type: type | StrawberryType
|
|
561
553
|
) -> GraphQLType:
|
|
562
554
|
type_: GraphQLType
|
|
563
555
|
|
|
@@ -596,9 +588,9 @@ class QueryCodegen:
|
|
|
596
588
|
return type_
|
|
597
589
|
|
|
598
590
|
def _collect_type_from_variable(
|
|
599
|
-
self, variable_type: TypeNode, parent_type:
|
|
591
|
+
self, variable_type: TypeNode, parent_type: TypeNode | None = None
|
|
600
592
|
) -> GraphQLType:
|
|
601
|
-
type_:
|
|
593
|
+
type_: GraphQLType | None = None
|
|
602
594
|
|
|
603
595
|
if isinstance(variable_type, ListTypeNode):
|
|
604
596
|
type_ = GraphQLList(
|
|
@@ -637,11 +629,9 @@ class QueryCodegen:
|
|
|
637
629
|
)
|
|
638
630
|
|
|
639
631
|
def _unwrap_type(
|
|
640
|
-
self, type_:
|
|
641
|
-
) -> tuple[
|
|
642
|
-
|
|
643
|
-
]:
|
|
644
|
-
wrapper: Optional[Callable[[GraphQLType], GraphQLType]] = None
|
|
632
|
+
self, type_: type | StrawberryType
|
|
633
|
+
) -> tuple[type | StrawberryType, Callable[[GraphQLType], GraphQLType] | None]:
|
|
634
|
+
wrapper: Callable[[GraphQLType], GraphQLType] | None = None
|
|
645
635
|
|
|
646
636
|
if isinstance(type_, StrawberryOptional):
|
|
647
637
|
type_, previous_wrapper = self._unwrap_type(type_.of_type)
|
|
@@ -738,7 +728,7 @@ class QueryCodegen:
|
|
|
738
728
|
selection: HasSelectionSet,
|
|
739
729
|
parent_type: StrawberryObjectDefinition,
|
|
740
730
|
class_name: str,
|
|
741
|
-
) ->
|
|
731
|
+
) -> GraphQLObjectType | GraphQLUnion:
|
|
742
732
|
sub_types = self._collect_types_using_fragments(
|
|
743
733
|
selection, parent_type, class_name
|
|
744
734
|
)
|
|
@@ -773,7 +763,7 @@ class QueryCodegen:
|
|
|
773
763
|
)
|
|
774
764
|
|
|
775
765
|
current_type = graph_ql_object_type_factory(class_name)
|
|
776
|
-
fields: list[
|
|
766
|
+
fields: list[GraphQLFragmentSpread | GraphQLField] = []
|
|
777
767
|
|
|
778
768
|
for sub_selection in selection_set.selections:
|
|
779
769
|
if isinstance(sub_selection, FragmentSpreadNode):
|
|
@@ -844,7 +834,7 @@ class QueryCodegen:
|
|
|
844
834
|
list(common_fields),
|
|
845
835
|
graphql_typename=type_condition_name,
|
|
846
836
|
)
|
|
847
|
-
fields: list[
|
|
837
|
+
fields: list[GraphQLFragmentSpread | GraphQLField] = []
|
|
848
838
|
|
|
849
839
|
for sub_selection in fragment.selection_set.selections:
|
|
850
840
|
if isinstance(sub_selection, FragmentSpreadNode):
|
|
@@ -899,7 +889,7 @@ class QueryCodegen:
|
|
|
899
889
|
return sub_types
|
|
900
890
|
|
|
901
891
|
def _collect_scalar(
|
|
902
|
-
self, scalar_definition: ScalarDefinition, python_type:
|
|
892
|
+
self, scalar_definition: ScalarDefinition, python_type: type | None
|
|
903
893
|
) -> GraphQLScalar:
|
|
904
894
|
graphql_scalar = GraphQLScalar(scalar_definition.name, python_type=python_type)
|
|
905
895
|
|
strawberry/codegen/types.py
CHANGED
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
from __future__ import annotations
|
|
2
2
|
|
|
3
3
|
from dataclasses import dataclass, field
|
|
4
|
-
from typing import TYPE_CHECKING,
|
|
4
|
+
from typing import TYPE_CHECKING, TypeAlias
|
|
5
5
|
|
|
6
6
|
if TYPE_CHECKING:
|
|
7
7
|
from collections.abc import Mapping
|
|
8
8
|
from enum import EnumMeta
|
|
9
|
-
from
|
|
9
|
+
from typing import Literal
|
|
10
10
|
|
|
11
11
|
from strawberry.types.unset import UnsetType
|
|
12
12
|
|
|
@@ -30,9 +30,9 @@ class GraphQLUnion:
|
|
|
30
30
|
@dataclass
|
|
31
31
|
class GraphQLField:
|
|
32
32
|
name: str
|
|
33
|
-
alias:
|
|
33
|
+
alias: str | None
|
|
34
34
|
type: GraphQLType
|
|
35
|
-
default_value:
|
|
35
|
+
default_value: GraphQLArgumentValue | None = None
|
|
36
36
|
|
|
37
37
|
|
|
38
38
|
@dataclass
|
|
@@ -44,7 +44,7 @@ class GraphQLFragmentSpread:
|
|
|
44
44
|
class GraphQLObjectType:
|
|
45
45
|
name: str
|
|
46
46
|
fields: list[GraphQLField] = field(default_factory=list)
|
|
47
|
-
graphql_typename:
|
|
47
|
+
graphql_typename: str | None = None
|
|
48
48
|
|
|
49
49
|
|
|
50
50
|
# Subtype of GraphQLObjectType.
|
|
@@ -54,7 +54,7 @@ class GraphQLObjectType:
|
|
|
54
54
|
class GraphQLFragmentType(GraphQLObjectType):
|
|
55
55
|
name: str
|
|
56
56
|
fields: list[GraphQLField] = field(default_factory=list)
|
|
57
|
-
graphql_typename:
|
|
57
|
+
graphql_typename: str | None = None
|
|
58
58
|
on: str = ""
|
|
59
59
|
|
|
60
60
|
def __post_init__(self) -> None:
|
|
@@ -74,23 +74,23 @@ class GraphQLEnum:
|
|
|
74
74
|
@dataclass
|
|
75
75
|
class GraphQLScalar:
|
|
76
76
|
name: str
|
|
77
|
-
python_type:
|
|
77
|
+
python_type: type | None
|
|
78
78
|
|
|
79
79
|
|
|
80
|
-
GraphQLType =
|
|
81
|
-
GraphQLObjectType
|
|
82
|
-
GraphQLEnum
|
|
83
|
-
GraphQLScalar
|
|
84
|
-
GraphQLOptional
|
|
85
|
-
GraphQLList
|
|
86
|
-
GraphQLUnion
|
|
87
|
-
|
|
80
|
+
GraphQLType: TypeAlias = (
|
|
81
|
+
GraphQLObjectType
|
|
82
|
+
| GraphQLEnum
|
|
83
|
+
| GraphQLScalar
|
|
84
|
+
| GraphQLOptional
|
|
85
|
+
| GraphQLList
|
|
86
|
+
| GraphQLUnion
|
|
87
|
+
)
|
|
88
88
|
|
|
89
89
|
|
|
90
90
|
@dataclass
|
|
91
91
|
class GraphQLFieldSelection:
|
|
92
92
|
field: str
|
|
93
|
-
alias:
|
|
93
|
+
alias: str | None
|
|
94
94
|
selections: list[GraphQLSelection]
|
|
95
95
|
directives: list[GraphQLDirective]
|
|
96
96
|
arguments: list[GraphQLArgument]
|
|
@@ -102,9 +102,9 @@ class GraphQLInlineFragment:
|
|
|
102
102
|
selections: list[GraphQLSelection]
|
|
103
103
|
|
|
104
104
|
|
|
105
|
-
GraphQLSelection =
|
|
106
|
-
GraphQLFieldSelection
|
|
107
|
-
|
|
105
|
+
GraphQLSelection: TypeAlias = (
|
|
106
|
+
GraphQLFieldSelection | GraphQLInlineFragment | GraphQLFragmentSpread
|
|
107
|
+
)
|
|
108
108
|
|
|
109
109
|
|
|
110
110
|
@dataclass
|
|
@@ -125,7 +125,7 @@ class GraphQLFloatValue:
|
|
|
125
125
|
@dataclass
|
|
126
126
|
class GraphQLEnumValue:
|
|
127
127
|
name: str
|
|
128
|
-
enum_type:
|
|
128
|
+
enum_type: str | None = None
|
|
129
129
|
|
|
130
130
|
|
|
131
131
|
@dataclass
|
|
@@ -155,17 +155,17 @@ class GraphQLVariableReference:
|
|
|
155
155
|
value: str
|
|
156
156
|
|
|
157
157
|
|
|
158
|
-
GraphQLArgumentValue =
|
|
159
|
-
GraphQLStringValue
|
|
160
|
-
GraphQLNullValue
|
|
161
|
-
GraphQLIntValue
|
|
162
|
-
GraphQLVariableReference
|
|
163
|
-
GraphQLFloatValue
|
|
164
|
-
GraphQLListValue
|
|
165
|
-
GraphQLEnumValue
|
|
166
|
-
GraphQLBoolValue
|
|
167
|
-
GraphQLObjectValue
|
|
168
|
-
|
|
158
|
+
GraphQLArgumentValue: TypeAlias = (
|
|
159
|
+
GraphQLStringValue
|
|
160
|
+
| GraphQLNullValue
|
|
161
|
+
| GraphQLIntValue
|
|
162
|
+
| GraphQLVariableReference
|
|
163
|
+
| GraphQLFloatValue
|
|
164
|
+
| GraphQLListValue
|
|
165
|
+
| GraphQLEnumValue
|
|
166
|
+
| GraphQLBoolValue
|
|
167
|
+
| GraphQLObjectValue
|
|
168
|
+
)
|
|
169
169
|
|
|
170
170
|
|
|
171
171
|
@dataclass
|
|
@@ -194,7 +194,7 @@ class GraphQLOperation:
|
|
|
194
194
|
directives: list[GraphQLDirective]
|
|
195
195
|
variables: list[GraphQLVariable]
|
|
196
196
|
type: GraphQLObjectType
|
|
197
|
-
variables_type:
|
|
197
|
+
variables_type: GraphQLObjectType | None
|
|
198
198
|
|
|
199
199
|
|
|
200
200
|
__all__ = [
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
from __future__ import annotations
|
|
2
2
|
|
|
3
|
-
from typing import TYPE_CHECKING
|
|
3
|
+
from typing import TYPE_CHECKING
|
|
4
4
|
|
|
5
5
|
import libcst as cst
|
|
6
6
|
import libcst.matchers as m
|
|
@@ -50,7 +50,7 @@ class ConvertUnionToAnnotatedUnion(VisitorBasedCodemodCommand):
|
|
|
50
50
|
|
|
51
51
|
super().__init__(context)
|
|
52
52
|
|
|
53
|
-
def visit_Module(self, node: cst.Module) ->
|
|
53
|
+
def visit_Module(self, node: cst.Module) -> bool | None: # noqa: N802
|
|
54
54
|
self._is_using_named_import = False
|
|
55
55
|
|
|
56
56
|
return super().visit_Module(node)
|