strawberry-graphql 0.235.2__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 -19
- 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 +6 -0
- strawberry/http/__init__.py +9 -0
- strawberry/http/async_base_view.py +4 -3
- strawberry/http/base.py +3 -0
- 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 +3 -0
- 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 +4 -2
- 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.2.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.2.dist-info/RECORD +0 -252
- {strawberry_graphql-0.235.2.dist-info → strawberry_graphql-0.236.0.dist-info}/LICENSE +0 -0
- {strawberry_graphql-0.235.2.dist-info → strawberry_graphql-0.236.0.dist-info}/WHEEL +0 -0
- {strawberry_graphql-0.235.2.dist-info → strawberry_graphql-0.236.0.dist-info}/entry_points.txt +0 -0
@@ -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
|
+
]
|
@@ -16,25 +16,28 @@ from typing import (
|
|
16
16
|
from typing_extensions import Annotated, get_args, get_origin
|
17
17
|
|
18
18
|
from strawberry.annotation import StrawberryAnnotation
|
19
|
-
from strawberry.
|
20
|
-
from strawberry.
|
21
|
-
from strawberry.
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
from .
|
19
|
+
from strawberry.exceptions import MultipleStrawberryArgumentsError, UnsupportedTypeError
|
20
|
+
from strawberry.scalars import is_scalar
|
21
|
+
from strawberry.types.base import (
|
22
|
+
StrawberryList,
|
23
|
+
StrawberryOptional,
|
24
|
+
has_object_definition,
|
25
|
+
)
|
26
|
+
from strawberry.types.enum import EnumDefinition
|
27
|
+
from strawberry.types.lazy_type import LazyType, StrawberryLazyReference
|
28
|
+
from strawberry.types.unset import UNSET as _deprecated_UNSET
|
29
|
+
from strawberry.types.unset import _deprecated_is_unset # noqa # type: ignore
|
27
30
|
|
28
31
|
if TYPE_CHECKING:
|
29
|
-
from strawberry.custom_scalar import ScalarDefinition, ScalarWrapper
|
30
32
|
from strawberry.schema.config import StrawberryConfig
|
31
|
-
from strawberry.
|
33
|
+
from strawberry.types.base import StrawberryType
|
34
|
+
from strawberry.types.scalar import ScalarDefinition, ScalarWrapper
|
32
35
|
|
33
36
|
|
34
37
|
DEPRECATED_NAMES: Dict[str, str] = {
|
35
38
|
"UNSET": (
|
36
39
|
"importing `UNSET` from `strawberry.arguments` is deprecated, "
|
37
|
-
"import instead from `strawberry` or from `strawberry.unset`"
|
40
|
+
"import instead from `strawberry` or from `strawberry.types.unset`"
|
38
41
|
),
|
39
42
|
"is_unset": "`is_unset` is deprecated use `value is UNSET` instead",
|
40
43
|
}
|
@@ -202,8 +205,8 @@ def convert_arguments(
|
|
202
205
|
"""Converts a nested dictionary to a dictionary of actual types.
|
203
206
|
|
204
207
|
It deals with conversion of input types to proper dataclasses and
|
205
|
-
also uses a sentinel value for unset values.
|
206
|
-
|
208
|
+
also uses a sentinel value for unset values.
|
209
|
+
"""
|
207
210
|
if not arguments:
|
208
211
|
return {}
|
209
212
|
|
@@ -234,6 +237,34 @@ def argument(
|
|
234
237
|
directives: Iterable[object] = (),
|
235
238
|
metadata: Optional[Mapping[Any, Any]] = None,
|
236
239
|
) -> StrawberryArgumentAnnotation:
|
240
|
+
"""Function to add metadata to an argument, like a description or deprecation reason.
|
241
|
+
|
242
|
+
Args:
|
243
|
+
description: The GraphQL description of the argument
|
244
|
+
name: The GraphQL name of the argument
|
245
|
+
deprecation_reason: The reason why this argument is deprecated,
|
246
|
+
setting this will mark the argument as deprecated
|
247
|
+
directives: The directives to attach to the argument
|
248
|
+
metadata: Metadata to attach to the argument, this can be used
|
249
|
+
to store custom data that can be used by custom logic or plugins
|
250
|
+
|
251
|
+
Returns:
|
252
|
+
A StrawberryArgumentAnnotation object that can be used to customise an argument
|
253
|
+
|
254
|
+
Example:
|
255
|
+
```python
|
256
|
+
import strawberry
|
257
|
+
|
258
|
+
|
259
|
+
@strawberry.type
|
260
|
+
class Query:
|
261
|
+
@strawberry.field
|
262
|
+
def example(
|
263
|
+
self, info, value: int = strawberry.argument(description="The value")
|
264
|
+
) -> int:
|
265
|
+
return value
|
266
|
+
```
|
267
|
+
"""
|
237
268
|
return StrawberryArgumentAnnotation(
|
238
269
|
description=description,
|
239
270
|
name=name,
|
@@ -3,9 +3,8 @@ from __future__ import annotations
|
|
3
3
|
from typing import Any, Optional, Union, cast
|
4
4
|
from typing_extensions import Annotated, get_args, get_origin
|
5
5
|
|
6
|
-
from strawberry.
|
7
|
-
|
8
|
-
from .annotation import StrawberryAnnotation
|
6
|
+
from strawberry.annotation import StrawberryAnnotation
|
7
|
+
from strawberry.types.base import StrawberryType
|
9
8
|
|
10
9
|
|
11
10
|
class StrawberryAutoMeta(type):
|
@@ -77,3 +76,22 @@ class StrawberryAuto(metaclass=StrawberryAutoMeta):
|
|
77
76
|
|
78
77
|
|
79
78
|
auto = Annotated[Any, StrawberryAuto()]
|
79
|
+
"""Special marker for automatic annotation.
|
80
|
+
|
81
|
+
A special value that can be used to automatically infer the type of a field
|
82
|
+
when using integrations like Strawberry Django or Strawberry Pydantic.
|
83
|
+
|
84
|
+
Example:
|
85
|
+
```python
|
86
|
+
import strawberry
|
87
|
+
|
88
|
+
from my_user_app import models
|
89
|
+
|
90
|
+
|
91
|
+
@strawberry.django.type(models.User)
|
92
|
+
class User:
|
93
|
+
name: strawberry.auto
|
94
|
+
```
|
95
|
+
"""
|
96
|
+
|
97
|
+
__all__ = ["auto"]
|