strawberry-graphql 0.235.1.dev1719337273__py3-none-any.whl → 0.236.0__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.
- strawberry/__init__.py +17 -11
- strawberry/aiohttp/handlers/graphql_transport_ws_handler.py +3 -0
- strawberry/aiohttp/handlers/graphql_ws_handler.py +3 -0
- strawberry/aiohttp/test/client.py +3 -0
- strawberry/aiohttp/views.py +3 -0
- strawberry/annotation.py +19 -22
- strawberry/asgi/__init__.py +3 -3
- strawberry/asgi/handlers/graphql_transport_ws_handler.py +3 -0
- strawberry/asgi/handlers/graphql_ws_handler.py +3 -0
- strawberry/asgi/test/client.py +3 -0
- strawberry/chalice/views.py +12 -3
- strawberry/channels/handlers/__init__.py +0 -0
- strawberry/channels/handlers/base.py +5 -5
- strawberry/channels/handlers/graphql_transport_ws_handler.py +3 -0
- strawberry/channels/handlers/graphql_ws_handler.py +3 -0
- strawberry/channels/handlers/http_handler.py +5 -2
- strawberry/channels/handlers/ws_handler.py +4 -1
- strawberry/channels/router.py +9 -5
- strawberry/channels/testing.py +11 -4
- strawberry/cli/commands/upgrade/__init__.py +13 -5
- strawberry/cli/commands/upgrade/_fake_progress.py +2 -1
- strawberry/cli/commands/upgrade/_run_codemod.py +18 -1
- strawberry/codegen/exceptions.py +8 -0
- strawberry/codegen/query_codegen.py +16 -7
- strawberry/codegen/types.py +32 -1
- strawberry/codemods/update_imports.py +136 -0
- strawberry/dataloader.py +13 -0
- strawberry/directive.py +52 -4
- strawberry/django/context.py +4 -1
- strawberry/django/test/client.py +3 -0
- strawberry/django/views.py +3 -0
- strawberry/exceptions/__init__.py +5 -5
- strawberry/exceptions/duplicated_type_name.py +1 -1
- strawberry/exceptions/invalid_argument_type.py +3 -3
- strawberry/exceptions/invalid_union_type.py +5 -6
- strawberry/exceptions/missing_arguments_annotations.py +1 -1
- strawberry/exceptions/missing_dependencies.py +10 -2
- strawberry/exceptions/missing_return_annotation.py +1 -1
- strawberry/exceptions/permission_fail_silently_requires_optional.py +3 -3
- strawberry/exceptions/scalar_already_registered.py +1 -1
- strawberry/exceptions/unresolved_field_type.py +2 -2
- strawberry/exceptions/utils/source_finder.py +5 -2
- strawberry/experimental/pydantic/conversion.py +5 -5
- strawberry/experimental/pydantic/conversion_types.py +4 -2
- strawberry/experimental/pydantic/error_type.py +2 -2
- strawberry/experimental/pydantic/fields.py +2 -2
- strawberry/experimental/pydantic/object_type.py +11 -7
- strawberry/experimental/pydantic/utils.py +4 -5
- strawberry/ext/dataclasses/dataclasses.py +2 -1
- strawberry/ext/mypy_plugin.py +10 -8
- strawberry/extensions/add_validation_rules.py +27 -23
- strawberry/extensions/base_extension.py +6 -4
- strawberry/extensions/directives.py +4 -1
- strawberry/extensions/disable_validation.py +15 -12
- strawberry/extensions/field_extension.py +11 -5
- strawberry/extensions/mask_errors.py +3 -0
- strawberry/extensions/max_aliases.py +21 -19
- strawberry/extensions/max_tokens.py +14 -16
- strawberry/extensions/parser_cache.py +22 -19
- strawberry/extensions/pyinstrument.py +4 -8
- strawberry/extensions/query_depth_limiter.py +22 -23
- strawberry/extensions/runner.py +3 -0
- strawberry/extensions/tracing/apollo.py +3 -0
- strawberry/extensions/tracing/datadog.py +7 -2
- strawberry/extensions/tracing/opentelemetry.py +3 -0
- strawberry/extensions/tracing/sentry.py +3 -0
- strawberry/extensions/tracing/utils.py +3 -0
- strawberry/extensions/utils.py +3 -0
- strawberry/extensions/validation_cache.py +23 -20
- strawberry/fastapi/context.py +3 -0
- strawberry/fastapi/handlers/graphql_transport_ws_handler.py +3 -0
- strawberry/fastapi/handlers/graphql_ws_handler.py +3 -0
- strawberry/fastapi/router.py +3 -0
- strawberry/federation/argument.py +4 -1
- strawberry/federation/enum.py +5 -3
- strawberry/federation/field.py +6 -3
- strawberry/federation/mutation.py +2 -0
- strawberry/federation/object_type.py +7 -4
- strawberry/federation/scalar.py +43 -20
- strawberry/federation/schema.py +12 -9
- strawberry/federation/schema_directive.py +2 -2
- strawberry/federation/schema_directives.py +19 -1
- strawberry/federation/types.py +5 -2
- strawberry/federation/union.py +27 -8
- strawberry/field_extensions/input_mutation.py +5 -2
- strawberry/file_uploads/scalars.py +3 -1
- strawberry/file_uploads/utils.py +3 -0
- strawberry/flask/views.py +8 -2
- strawberry/http/__init__.py +9 -0
- strawberry/http/async_base_view.py +4 -3
- strawberry/http/base.py +5 -7
- strawberry/http/exceptions.py +3 -0
- strawberry/http/ides.py +3 -0
- strawberry/http/sync_base_view.py +4 -3
- strawberry/http/temporal_response.py +3 -0
- strawberry/http/types.py +5 -2
- strawberry/http/typevars.py +3 -0
- strawberry/litestar/controller.py +6 -0
- strawberry/litestar/handlers/__init__.py +0 -0
- strawberry/litestar/handlers/graphql_transport_ws_handler.py +3 -0
- strawberry/litestar/handlers/graphql_ws_handler.py +3 -0
- strawberry/parent.py +27 -21
- strawberry/permission.py +70 -27
- strawberry/printer/ast_from_value.py +4 -1
- strawberry/printer/printer.py +8 -5
- strawberry/quart/views.py +3 -0
- strawberry/relay/exceptions.py +7 -0
- strawberry/relay/fields.py +70 -45
- strawberry/relay/types.py +78 -78
- strawberry/relay/utils.py +10 -1
- strawberry/resolvers.py +3 -0
- strawberry/sanic/context.py +3 -0
- strawberry/sanic/utils.py +10 -8
- strawberry/sanic/views.py +5 -9
- strawberry/scalars.py +6 -2
- strawberry/schema/base.py +7 -4
- strawberry/schema/compat.py +12 -2
- strawberry/schema/config.py +3 -0
- strawberry/schema/exceptions.py +3 -0
- strawberry/schema/execute.py +3 -0
- strawberry/schema/name_converter.py +12 -9
- strawberry/schema/schema.py +46 -9
- strawberry/schema/schema_converter.py +16 -14
- strawberry/schema/types/base_scalars.py +3 -1
- strawberry/schema/types/concrete_type.py +4 -4
- strawberry/schema/types/scalar.py +8 -1
- strawberry/schema/validation_rules/one_of.py +3 -0
- strawberry/schema_codegen/__init__.py +3 -0
- strawberry/schema_directive.py +2 -2
- strawberry/starlite/controller.py +3 -0
- strawberry/starlite/handlers/__init__.py +0 -0
- strawberry/starlite/handlers/graphql_transport_ws_handler.py +3 -0
- strawberry/starlite/handlers/graphql_ws_handler.py +3 -0
- strawberry/subscriptions/__init__.py +6 -0
- strawberry/subscriptions/protocols/graphql_transport_ws/__init__.py +5 -0
- strawberry/subscriptions/protocols/graphql_transport_ws/handlers.py +12 -17
- strawberry/subscriptions/protocols/graphql_transport_ws/types.py +21 -25
- strawberry/subscriptions/protocols/graphql_ws/__init__.py +14 -0
- strawberry/subscriptions/protocols/graphql_ws/handlers.py +8 -5
- strawberry/subscriptions/protocols/graphql_ws/types.py +11 -0
- strawberry/test/client.py +44 -29
- strawberry/tools/create_type.py +27 -8
- strawberry/tools/merge_types.py +5 -3
- strawberry/types/__init__.py +8 -1
- strawberry/{arguments.py → types/arguments.py} +44 -13
- strawberry/{auto.py → types/auto.py} +21 -3
- strawberry/types/{types.py → base.py} +234 -10
- strawberry/{enum.py → types/enum.py} +69 -9
- strawberry/types/execution.py +3 -0
- strawberry/{field.py → types/field.py} +46 -23
- strawberry/types/fields/resolver.py +2 -2
- strawberry/types/graphql.py +3 -0
- strawberry/types/info.py +50 -7
- strawberry/{lazy_type.py → types/lazy_type.py} +50 -0
- strawberry/types/mutation.py +351 -0
- strawberry/types/nodes.py +4 -2
- strawberry/{object_type.py → types/object_type.py} +108 -29
- strawberry/{private.py → types/private.py} +13 -6
- strawberry/{custom_scalar.py → types/scalar.py} +39 -23
- strawberry/types/type_resolver.py +21 -16
- strawberry/{union.py → types/union.py} +24 -9
- strawberry/{unset.py → types/unset.py} +20 -0
- strawberry/utils/aio.py +8 -0
- strawberry/utils/await_maybe.py +3 -0
- strawberry/utils/dataclasses.py +3 -0
- strawberry/utils/debug.py +5 -2
- strawberry/utils/deprecations.py +3 -0
- strawberry/utils/graphql_lexer.py +3 -0
- strawberry/utils/importer.py +3 -0
- strawberry/utils/inspect.py +39 -30
- strawberry/utils/logging.py +3 -0
- strawberry/utils/operation.py +3 -0
- strawberry/utils/str_converters.py +3 -0
- strawberry/utils/typing.py +33 -16
- {strawberry_graphql-0.235.1.dev1719337273.dist-info → strawberry_graphql-0.236.0.dist-info}/METADATA +1 -1
- strawberry_graphql-0.236.0.dist-info/RECORD +255 -0
- strawberry/mutation.py +0 -8
- strawberry/type.py +0 -232
- strawberry_graphql-0.235.1.dev1719337273.dist-info/RECORD +0 -252
- {strawberry_graphql-0.235.1.dev1719337273.dist-info → strawberry_graphql-0.236.0.dist-info}/LICENSE +0 -0
- {strawberry_graphql-0.235.1.dev1719337273.dist-info → strawberry_graphql-0.236.0.dist-info}/WHEEL +0 -0
- {strawberry_graphql-0.235.1.dev1719337273.dist-info → strawberry_graphql-0.236.0.dist-info}/entry_points.txt +0 -0
@@ -44,9 +44,6 @@ from graphql import (
|
|
44
44
|
from graphql.language.directive_locations import DirectiveLocation
|
45
45
|
|
46
46
|
from strawberry.annotation import StrawberryAnnotation
|
47
|
-
from strawberry.arguments import StrawberryArgument, convert_arguments
|
48
|
-
from strawberry.custom_scalar import ScalarWrapper
|
49
|
-
from strawberry.enum import EnumDefinition
|
50
47
|
from strawberry.exceptions import (
|
51
48
|
DuplicatedTypeName,
|
52
49
|
InvalidTypeInputForUnion,
|
@@ -55,21 +52,24 @@ from strawberry.exceptions import (
|
|
55
52
|
ScalarAlreadyRegisteredError,
|
56
53
|
UnresolvedFieldTypeError,
|
57
54
|
)
|
58
|
-
from strawberry.field import UNRESOLVED
|
59
|
-
from strawberry.lazy_type import LazyType
|
60
|
-
from strawberry.private import is_private
|
61
55
|
from strawberry.schema.types.scalar import _make_scalar_type
|
62
|
-
from strawberry.
|
56
|
+
from strawberry.types.arguments import StrawberryArgument, convert_arguments
|
57
|
+
from strawberry.types.base import (
|
63
58
|
StrawberryList,
|
59
|
+
StrawberryObjectDefinition,
|
64
60
|
StrawberryOptional,
|
65
61
|
StrawberryType,
|
66
62
|
get_object_definition,
|
67
63
|
has_object_definition,
|
68
64
|
)
|
65
|
+
from strawberry.types.enum import EnumDefinition
|
66
|
+
from strawberry.types.field import UNRESOLVED
|
69
67
|
from strawberry.types.info import Info
|
70
|
-
from strawberry.types.
|
71
|
-
from strawberry.
|
72
|
-
from strawberry.
|
68
|
+
from strawberry.types.lazy_type import LazyType
|
69
|
+
from strawberry.types.private import is_private
|
70
|
+
from strawberry.types.scalar import ScalarWrapper
|
71
|
+
from strawberry.types.union import StrawberryUnion
|
72
|
+
from strawberry.types.unset import UNSET
|
73
73
|
from strawberry.utils.await_maybe import await_maybe
|
74
74
|
|
75
75
|
from ..extensions.field_extension import build_field_extension_resolvers
|
@@ -85,12 +85,12 @@ if TYPE_CHECKING:
|
|
85
85
|
GraphQLScalarType,
|
86
86
|
)
|
87
87
|
|
88
|
-
from strawberry.custom_scalar import ScalarDefinition
|
89
88
|
from strawberry.directive import StrawberryDirective
|
90
|
-
from strawberry.enum import EnumValue
|
91
|
-
from strawberry.field import StrawberryField
|
92
89
|
from strawberry.schema.config import StrawberryConfig
|
93
90
|
from strawberry.schema_directive import StrawberrySchemaDirective
|
91
|
+
from strawberry.types.enum import EnumValue
|
92
|
+
from strawberry.types.field import StrawberryField
|
93
|
+
from strawberry.types.scalar import ScalarDefinition
|
94
94
|
|
95
95
|
|
96
96
|
FieldType = TypeVar(
|
@@ -681,7 +681,6 @@ class GraphQLCoreConverter:
|
|
681
681
|
|
682
682
|
def wrap_field_extensions() -> Callable[..., Any]:
|
683
683
|
"""Wrap the provided field resolver with the middleware."""
|
684
|
-
|
685
684
|
for extension in field.extensions:
|
686
685
|
extension.apply(field)
|
687
686
|
|
@@ -999,3 +998,6 @@ class GraphQLCoreConverter:
|
|
999
998
|
second_origin = None
|
1000
999
|
|
1001
1000
|
raise DuplicatedTypeName(first_origin, second_origin, name)
|
1001
|
+
|
1002
|
+
|
1003
|
+
__all__ = ["GraphQLCoreConverter"]
|
@@ -7,7 +7,7 @@ from typing import Callable
|
|
7
7
|
import dateutil.parser
|
8
8
|
from graphql import GraphQLError
|
9
9
|
|
10
|
-
from strawberry.
|
10
|
+
from strawberry.types.scalar import scalar
|
11
11
|
|
12
12
|
|
13
13
|
def wrap_parser(parser: Callable, type_: str) -> Callable:
|
@@ -80,3 +80,5 @@ Void = scalar(
|
|
80
80
|
parse_value=_verify_void,
|
81
81
|
description="Represents NULL values",
|
82
82
|
)
|
83
|
+
|
84
|
+
__all__ = ["Date", "DateTime", "Time", "Decimal", "UUID", "Void"]
|
@@ -6,10 +6,10 @@ from typing import TYPE_CHECKING, Dict, Union
|
|
6
6
|
from graphql import GraphQLField, GraphQLInputField, GraphQLType
|
7
7
|
|
8
8
|
if TYPE_CHECKING:
|
9
|
-
from strawberry.
|
10
|
-
from strawberry.enum import EnumDefinition
|
11
|
-
from strawberry.types.
|
12
|
-
from strawberry.union import StrawberryUnion
|
9
|
+
from strawberry.types.base import StrawberryObjectDefinition
|
10
|
+
from strawberry.types.enum import EnumDefinition
|
11
|
+
from strawberry.types.scalar import ScalarDefinition
|
12
|
+
from strawberry.types.union import StrawberryUnion
|
13
13
|
|
14
14
|
Field = Union[GraphQLInputField, GraphQLField]
|
15
15
|
|
@@ -12,11 +12,11 @@ from graphql import (
|
|
12
12
|
GraphQLString,
|
13
13
|
)
|
14
14
|
|
15
|
-
from strawberry.custom_scalar import ScalarDefinition, scalar
|
16
15
|
from strawberry.file_uploads.scalars import Upload
|
17
16
|
from strawberry.relay.types import GlobalID
|
18
17
|
from strawberry.scalars import ID
|
19
18
|
from strawberry.schema.types import base_scalars
|
19
|
+
from strawberry.types.scalar import ScalarDefinition, scalar
|
20
20
|
|
21
21
|
|
22
22
|
def _make_scalar_type(definition: ScalarDefinition) -> GraphQLScalarType:
|
@@ -78,3 +78,10 @@ DEFAULT_SCALAR_REGISTRY: Dict[object, ScalarDefinition] = {
|
|
78
78
|
)
|
79
79
|
),
|
80
80
|
}
|
81
|
+
|
82
|
+
__all__ = [
|
83
|
+
"DEFAULT_SCALAR_REGISTRY",
|
84
|
+
"_get_scalar_definition",
|
85
|
+
"_make_scalar_definition",
|
86
|
+
"_make_scalar_type",
|
87
|
+
]
|
strawberry/schema_directive.py
CHANGED
@@ -3,11 +3,11 @@ from enum import Enum
|
|
3
3
|
from typing import Callable, List, Optional, Type, TypeVar
|
4
4
|
from typing_extensions import dataclass_transform
|
5
5
|
|
6
|
-
from strawberry.
|
6
|
+
from strawberry.types.field import StrawberryField, field
|
7
|
+
from strawberry.types.object_type import _wrap_dataclass
|
7
8
|
from strawberry.types.type_resolver import _get_fields
|
8
9
|
|
9
10
|
from .directive import directive_field
|
10
|
-
from .field import StrawberryField, field
|
11
11
|
|
12
12
|
|
13
13
|
class Location(Enum):
|
File without changes
|
@@ -30,7 +30,7 @@ from strawberry.subscriptions.protocols.graphql_transport_ws.types import (
|
|
30
30
|
SubscribeMessagePayload,
|
31
31
|
)
|
32
32
|
from strawberry.types.graphql import OperationType
|
33
|
-
from strawberry.unset import UNSET
|
33
|
+
from strawberry.types.unset import UNSET
|
34
34
|
from strawberry.utils.debug import pretty_print_graphql_operation
|
35
35
|
from strawberry.utils.operation import get_operation_type
|
36
36
|
|
@@ -66,23 +66,23 @@ class BaseGraphQLTransportWSHandler(ABC):
|
|
66
66
|
|
67
67
|
@abstractmethod
|
68
68
|
async def get_context(self) -> Any:
|
69
|
-
"""Return the operations context"""
|
69
|
+
"""Return the operations context."""
|
70
70
|
|
71
71
|
@abstractmethod
|
72
72
|
async def get_root_value(self) -> Any:
|
73
|
-
"""Return the schemas root value"""
|
73
|
+
"""Return the schemas root value."""
|
74
74
|
|
75
75
|
@abstractmethod
|
76
76
|
async def send_json(self, data: dict) -> None:
|
77
|
-
"""Send the data JSON encoded to the WebSocket client"""
|
77
|
+
"""Send the data JSON encoded to the WebSocket client."""
|
78
78
|
|
79
79
|
@abstractmethod
|
80
80
|
async def close(self, code: int, reason: str) -> None:
|
81
|
-
"""Close the WebSocket with the passed code and reason"""
|
81
|
+
"""Close the WebSocket with the passed code and reason."""
|
82
82
|
|
83
83
|
@abstractmethod
|
84
84
|
async def handle_request(self) -> Any:
|
85
|
-
"""Handle the request this instance was created for"""
|
85
|
+
"""Handle the request this instance was created for."""
|
86
86
|
|
87
87
|
async def handle(self) -> Any:
|
88
88
|
return await self.handle_request()
|
@@ -286,10 +286,7 @@ class BaseGraphQLTransportWSHandler(ABC):
|
|
286
286
|
async def operation_task(
|
287
287
|
self, result_source: AsyncGenerator, operation: Operation
|
288
288
|
) -> None:
|
289
|
-
"""
|
290
|
-
Operation task top level method. Cleans up and de-registers the operation
|
291
|
-
once it is done.
|
292
|
-
"""
|
289
|
+
"""The operation task's top level method. Cleans-up and de-registers the operation once it is done."""
|
293
290
|
# TODO: Handle errors in this method using self.handle_task_exception()
|
294
291
|
try:
|
295
292
|
await self.handle_async_results(result_source, operation)
|
@@ -371,9 +368,7 @@ class BaseGraphQLTransportWSHandler(ABC):
|
|
371
368
|
# websocket handler Task.
|
372
369
|
|
373
370
|
async def reap_completed_tasks(self) -> None:
|
374
|
-
"""
|
375
|
-
Await tasks that have completed
|
376
|
-
"""
|
371
|
+
"""Await tasks that have completed."""
|
377
372
|
tasks, self.completed_tasks = self.completed_tasks, []
|
378
373
|
for task in tasks:
|
379
374
|
with suppress(BaseException):
|
@@ -381,10 +376,7 @@ class BaseGraphQLTransportWSHandler(ABC):
|
|
381
376
|
|
382
377
|
|
383
378
|
class Operation:
|
384
|
-
"""
|
385
|
-
A class encapsulating a single operation with its id.
|
386
|
-
Helps enforce protocol state transition.
|
387
|
-
"""
|
379
|
+
"""A class encapsulating a single operation with its id. Helps enforce protocol state transition."""
|
388
380
|
|
389
381
|
__slots__ = ["handler", "id", "operation_type", "completed", "task"]
|
390
382
|
|
@@ -408,3 +400,6 @@ class Operation:
|
|
408
400
|
# de-register the operation _before_ sending the final message
|
409
401
|
self.handler.forget_id(self.id)
|
410
402
|
await self.handler.send_message(message)
|
403
|
+
|
404
|
+
|
405
|
+
__all__ = ["BaseGraphQLTransportWSHandler", "Operation"]
|
@@ -3,7 +3,7 @@ from __future__ import annotations
|
|
3
3
|
from dataclasses import asdict, dataclass
|
4
4
|
from typing import TYPE_CHECKING, Any, Dict, List, Optional
|
5
5
|
|
6
|
-
from strawberry.unset import UNSET
|
6
|
+
from strawberry.types.unset import UNSET
|
7
7
|
|
8
8
|
if TYPE_CHECKING:
|
9
9
|
from graphql import GraphQLFormattedError
|
@@ -21,9 +21,7 @@ class GraphQLTransportMessage:
|
|
21
21
|
|
22
22
|
@dataclass
|
23
23
|
class ConnectionInitMessage(GraphQLTransportMessage):
|
24
|
-
"""
|
25
|
-
Direction: Client -> Server
|
26
|
-
"""
|
24
|
+
"""Direction: Client -> Server."""
|
27
25
|
|
28
26
|
payload: Optional[Dict[str, Any]] = UNSET
|
29
27
|
type: str = "connection_init"
|
@@ -31,9 +29,7 @@ class ConnectionInitMessage(GraphQLTransportMessage):
|
|
31
29
|
|
32
30
|
@dataclass
|
33
31
|
class ConnectionAckMessage(GraphQLTransportMessage):
|
34
|
-
"""
|
35
|
-
Direction: Server -> Client
|
36
|
-
"""
|
32
|
+
"""Direction: Server -> Client."""
|
37
33
|
|
38
34
|
payload: Optional[Dict[str, Any]] = UNSET
|
39
35
|
type: str = "connection_ack"
|
@@ -41,9 +37,7 @@ class ConnectionAckMessage(GraphQLTransportMessage):
|
|
41
37
|
|
42
38
|
@dataclass
|
43
39
|
class PingMessage(GraphQLTransportMessage):
|
44
|
-
"""
|
45
|
-
Direction: bidirectional
|
46
|
-
"""
|
40
|
+
"""Direction: bidirectional."""
|
47
41
|
|
48
42
|
payload: Optional[Dict[str, Any]] = UNSET
|
49
43
|
type: str = "ping"
|
@@ -51,9 +45,7 @@ class PingMessage(GraphQLTransportMessage):
|
|
51
45
|
|
52
46
|
@dataclass
|
53
47
|
class PongMessage(GraphQLTransportMessage):
|
54
|
-
"""
|
55
|
-
Direction: bidirectional
|
56
|
-
"""
|
48
|
+
"""Direction: bidirectional."""
|
57
49
|
|
58
50
|
payload: Optional[Dict[str, Any]] = UNSET
|
59
51
|
type: str = "pong"
|
@@ -69,9 +61,7 @@ class SubscribeMessagePayload:
|
|
69
61
|
|
70
62
|
@dataclass
|
71
63
|
class SubscribeMessage(GraphQLTransportMessage):
|
72
|
-
"""
|
73
|
-
Direction: Client -> Server
|
74
|
-
"""
|
64
|
+
"""Direction: Client -> Server."""
|
75
65
|
|
76
66
|
id: str
|
77
67
|
payload: SubscribeMessagePayload
|
@@ -80,9 +70,7 @@ class SubscribeMessage(GraphQLTransportMessage):
|
|
80
70
|
|
81
71
|
@dataclass
|
82
72
|
class NextMessage(GraphQLTransportMessage):
|
83
|
-
"""
|
84
|
-
Direction: Server -> Client
|
85
|
-
"""
|
73
|
+
"""Direction: Server -> Client."""
|
86
74
|
|
87
75
|
id: str
|
88
76
|
payload: Dict[str, Any] # TODO: shape like FormattedExecutionResult
|
@@ -94,9 +82,7 @@ class NextMessage(GraphQLTransportMessage):
|
|
94
82
|
|
95
83
|
@dataclass
|
96
84
|
class ErrorMessage(GraphQLTransportMessage):
|
97
|
-
"""
|
98
|
-
Direction: Server -> Client
|
99
|
-
"""
|
85
|
+
"""Direction: Server -> Client."""
|
100
86
|
|
101
87
|
id: str
|
102
88
|
payload: List[GraphQLFormattedError]
|
@@ -105,9 +91,19 @@ class ErrorMessage(GraphQLTransportMessage):
|
|
105
91
|
|
106
92
|
@dataclass
|
107
93
|
class CompleteMessage(GraphQLTransportMessage):
|
108
|
-
"""
|
109
|
-
Direction: bidirectional
|
110
|
-
"""
|
94
|
+
"""Direction: bidirectional."""
|
111
95
|
|
112
96
|
id: str
|
113
97
|
type: str = "complete"
|
98
|
+
|
99
|
+
|
100
|
+
__all__ = [
|
101
|
+
"ConnectionInitMessage",
|
102
|
+
"ConnectionAckMessage",
|
103
|
+
"PingMessage",
|
104
|
+
"PongMessage",
|
105
|
+
"SubscribeMessage",
|
106
|
+
"NextMessage",
|
107
|
+
"ErrorMessage",
|
108
|
+
"CompleteMessage",
|
109
|
+
]
|
@@ -8,3 +8,17 @@ GQL_DATA = "data"
|
|
8
8
|
GQL_ERROR = "error"
|
9
9
|
GQL_COMPLETE = "complete"
|
10
10
|
GQL_STOP = "stop"
|
11
|
+
|
12
|
+
|
13
|
+
__all__ = [
|
14
|
+
"GQL_CONNECTION_INIT",
|
15
|
+
"GQL_CONNECTION_ACK",
|
16
|
+
"GQL_CONNECTION_ERROR",
|
17
|
+
"GQL_CONNECTION_TERMINATE",
|
18
|
+
"GQL_CONNECTION_KEEP_ALIVE",
|
19
|
+
"GQL_START",
|
20
|
+
"GQL_DATA",
|
21
|
+
"GQL_ERROR",
|
22
|
+
"GQL_COMPLETE",
|
23
|
+
"GQL_STOP",
|
24
|
+
]
|
@@ -51,23 +51,23 @@ class BaseGraphQLWSHandler(ABC):
|
|
51
51
|
|
52
52
|
@abstractmethod
|
53
53
|
async def get_context(self) -> Any:
|
54
|
-
"""Return the operations context"""
|
54
|
+
"""Return the operations context."""
|
55
55
|
|
56
56
|
@abstractmethod
|
57
57
|
async def get_root_value(self) -> Any:
|
58
|
-
"""Return the schemas root value"""
|
58
|
+
"""Return the schemas root value."""
|
59
59
|
|
60
60
|
@abstractmethod
|
61
61
|
async def send_json(self, data: OperationMessage) -> None:
|
62
|
-
"""Send the data JSON encoded to the WebSocket client"""
|
62
|
+
"""Send the data JSON encoded to the WebSocket client."""
|
63
63
|
|
64
64
|
@abstractmethod
|
65
65
|
async def close(self, code: int = 1000, reason: Optional[str] = None) -> None:
|
66
|
-
"""Close the WebSocket with the passed code and reason"""
|
66
|
+
"""Close the WebSocket with the passed code and reason."""
|
67
67
|
|
68
68
|
@abstractmethod
|
69
69
|
async def handle_request(self) -> Any:
|
70
|
-
"""Handle the request this instance was created for"""
|
70
|
+
"""Handle the request this instance was created for."""
|
71
71
|
|
72
72
|
async def handle(self) -> Any:
|
73
73
|
return await self.handle_request()
|
@@ -208,3 +208,6 @@ class BaseGraphQLWSHandler(ABC):
|
|
208
208
|
if payload is not None:
|
209
209
|
data["payload"] = payload
|
210
210
|
await self.send_json(data)
|
211
|
+
|
212
|
+
|
213
|
+
__all__ = ["BaseGraphQLWSHandler"]
|
@@ -38,3 +38,14 @@ class OperationMessage(TypedDict, total=False):
|
|
38
38
|
type: str
|
39
39
|
id: str
|
40
40
|
payload: OperationMessagePayload
|
41
|
+
|
42
|
+
|
43
|
+
__all__ = [
|
44
|
+
"ConnectionInitPayload",
|
45
|
+
"ConnectionErrorPayload",
|
46
|
+
"StartPayload",
|
47
|
+
"DataPayload",
|
48
|
+
"ErrorPayload",
|
49
|
+
"OperationMessagePayload",
|
50
|
+
"OperationMessage",
|
51
|
+
]
|
strawberry/test/client.py
CHANGED
@@ -91,47 +91,59 @@ class BaseGraphQLTestClient(ABC):
|
|
91
91
|
def _build_multipart_file_map(
|
92
92
|
variables: Dict[str, Mapping], files: Dict[str, object]
|
93
93
|
) -> Dict[str, List[str]]:
|
94
|
-
"""Creates the file mapping between the variables and the files objects passed
|
95
|
-
|
94
|
+
"""Creates the file mapping between the variables and the files objects passed as key arguments.
|
95
|
+
|
96
|
+
Args:
|
97
|
+
variables: A dictionary with the variables that are going to be passed to the
|
98
|
+
query.
|
99
|
+
files: A dictionary with the files that are going to be passed to the query.
|
96
100
|
|
97
101
|
Example usages:
|
98
102
|
|
99
|
-
|
100
|
-
|
101
|
-
|
102
|
-
|
103
|
+
```python
|
104
|
+
_build_multipart_file_map(variables={"textFile": None}, files={"textFile": f})
|
105
|
+
# {"textFile": ["variables.textFile"]}
|
106
|
+
```
|
103
107
|
|
104
108
|
If the variable is a list we have to enumerate files in the mapping
|
105
|
-
|
106
|
-
|
107
|
-
|
108
|
-
|
109
|
-
|
109
|
+
|
110
|
+
```python
|
111
|
+
_build_multipart_file_map(
|
112
|
+
variables={"files": [None, None]},
|
113
|
+
files={"file1": file1, "file2": file2},
|
114
|
+
)
|
115
|
+
# {"file1": ["variables.files.0"], "file2": ["variables.files.1"]}
|
116
|
+
```
|
110
117
|
|
111
118
|
If `variables` contains another keyword (a folder) we must include that keyword
|
112
119
|
in the mapping
|
113
|
-
|
114
|
-
|
115
|
-
|
116
|
-
|
117
|
-
|
118
|
-
|
119
|
-
|
120
|
-
|
120
|
+
|
121
|
+
```python
|
122
|
+
_build_multipart_file_map(
|
123
|
+
variables={"folder": {"files": [None, None]}},
|
124
|
+
files={"file1": file1, "file2": file2},
|
125
|
+
)
|
126
|
+
# {
|
127
|
+
# "file1": ["variables.files.folder.files.0"],
|
128
|
+
# "file2": ["variables.files.folder.files.1"]
|
129
|
+
# }
|
130
|
+
```
|
121
131
|
|
122
132
|
If `variables` includes both a list of files and other single values, we must
|
123
133
|
map them accordingly
|
124
|
-
>>> _build_multipart_file_map(
|
125
|
-
>>> variables={"files": [None, None], "textFile": None},
|
126
|
-
>>> files={"file1": file1, "file2": file2, "textFile": file3},
|
127
|
-
>>> )
|
128
|
-
... {
|
129
|
-
... "file1": ["variables.files.0"],
|
130
|
-
... "file2": ["variables.files.1"],
|
131
|
-
... "textFile": ["variables.textFile"],
|
132
|
-
... }
|
133
|
-
"""
|
134
134
|
|
135
|
+
```python
|
136
|
+
_build_multipart_file_map(
|
137
|
+
variables={"files": [None, None], "textFile": None},
|
138
|
+
files={"file1": file1, "file2": file2, "textFile": file3},
|
139
|
+
)
|
140
|
+
# {
|
141
|
+
# "file1": ["variables.files.0"],
|
142
|
+
# "file2": ["variables.files.1"],
|
143
|
+
# "textFile": ["variables.textFile"],
|
144
|
+
# }
|
145
|
+
```
|
146
|
+
"""
|
135
147
|
map: Dict[str, List[str]] = {}
|
136
148
|
for key, values in variables.items():
|
137
149
|
reference = key
|
@@ -167,3 +179,6 @@ class BaseGraphQLTestClient(ABC):
|
|
167
179
|
if type == "multipart":
|
168
180
|
return json.loads(response.content.decode())
|
169
181
|
return response.json()
|
182
|
+
|
183
|
+
|
184
|
+
__all__ = ["BaseGraphQLTestClient", "Response", "Body"]
|
strawberry/tools/create_type.py
CHANGED
@@ -2,7 +2,7 @@ import types
|
|
2
2
|
from typing import List, Optional, Sequence, Type
|
3
3
|
|
4
4
|
import strawberry
|
5
|
-
from strawberry.field import StrawberryField
|
5
|
+
from strawberry.types.field import StrawberryField
|
6
6
|
|
7
7
|
|
8
8
|
def create_type(
|
@@ -14,15 +14,31 @@ def create_type(
|
|
14
14
|
directives: Optional[Sequence[object]] = (),
|
15
15
|
extend: bool = False,
|
16
16
|
) -> Type:
|
17
|
-
"""Create a Strawberry type from a list of StrawberryFields
|
17
|
+
"""Create a Strawberry type from a list of StrawberryFields.
|
18
18
|
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
19
|
+
Args:
|
20
|
+
name: The GraphQL name of the type.
|
21
|
+
fields: The fields of the type.
|
22
|
+
is_input: Whether the type is an input type.
|
23
|
+
is_interface: Whether the type is an interface.
|
24
|
+
description: The GraphQL description of the type.
|
25
|
+
directives: The directives to attach to the type.
|
26
|
+
extend: Whether the type is an extension.
|
27
|
+
|
28
|
+
Example usage:
|
29
|
+
|
30
|
+
```python
|
31
|
+
import strawberry
|
32
|
+
|
33
|
+
|
34
|
+
@strawberry.field
|
35
|
+
def hello(info) -> str:
|
36
|
+
return "World"
|
25
37
|
|
38
|
+
|
39
|
+
Query = create_type(name="Query", fields=[hello])
|
40
|
+
```
|
41
|
+
"""
|
26
42
|
if not fields:
|
27
43
|
raise ValueError(f'Can\'t create type "{name}" with no fields')
|
28
44
|
|
@@ -55,3 +71,6 @@ def create_type(
|
|
55
71
|
directives=directives,
|
56
72
|
extend=extend,
|
57
73
|
)
|
74
|
+
|
75
|
+
|
76
|
+
__all__ = ["create_type"]
|
strawberry/tools/merge_types.py
CHANGED
@@ -4,11 +4,11 @@ from itertools import chain
|
|
4
4
|
from typing import Tuple
|
5
5
|
|
6
6
|
import strawberry
|
7
|
-
from strawberry.
|
7
|
+
from strawberry.types.base import has_object_definition
|
8
8
|
|
9
9
|
|
10
10
|
def merge_types(name: str, types: Tuple[type, ...]) -> type:
|
11
|
-
"""Merge multiple Strawberry types into one
|
11
|
+
"""Merge multiple Strawberry types into one.
|
12
12
|
|
13
13
|
For example, given two queries `A` and `B`, one can merge them into a
|
14
14
|
super type as follows:
|
@@ -20,7 +20,6 @@ def merge_types(name: str, types: Tuple[type, ...]) -> type:
|
|
20
20
|
class SuperQuery(B, A):
|
21
21
|
...
|
22
22
|
"""
|
23
|
-
|
24
23
|
if not types:
|
25
24
|
raise ValueError("Can't merge types if none are supplied")
|
26
25
|
|
@@ -35,3 +34,6 @@ def merge_types(name: str, types: Tuple[type, ...]) -> type:
|
|
35
34
|
)
|
36
35
|
|
37
36
|
return strawberry.type(type(name, types, {}))
|
37
|
+
|
38
|
+
|
39
|
+
__all__ = ["merge_types"]
|
strawberry/types/__init__.py
CHANGED
@@ -1,4 +1,11 @@
|
|
1
|
+
from .base import get_object_definition, has_object_definition
|
1
2
|
from .execution import ExecutionContext, ExecutionResult
|
2
3
|
from .info import Info
|
3
4
|
|
4
|
-
__all__ = [
|
5
|
+
__all__ = [
|
6
|
+
"ExecutionContext",
|
7
|
+
"ExecutionResult",
|
8
|
+
"Info",
|
9
|
+
"get_object_definition",
|
10
|
+
"has_object_definition",
|
11
|
+
]
|