11from sys import exc_info
22from typing import Any , Collection , Dict , List , Optional , Union , TYPE_CHECKING
33
4+ try :
5+ from typing import TypedDict
6+ except ImportError : # Python < 3.8
7+ from typing_extensions import TypedDict
8+
49if TYPE_CHECKING :
510 from ..language .ast import Node # noqa: F401
6- from ..language .location import SourceLocation # noqa: F401
11+ from ..language .location import (
12+ SourceLocation ,
13+ FormattedSourceLocation ,
14+ ) # noqa: F401
715 from ..language .source import Source # noqa: F401
816
9- __all__ = ["GraphQLError" ]
17+ __all__ = ["GraphQLError" , "GraphQLFormattedError" ]
18+
19+
20+ class GraphQLFormattedError (TypedDict , total = False ):
21+ """Formatted GraphQL error"""
22+
23+ # A short, human-readable summary of the problem that **SHOULD NOT** change
24+ # from occurrence to occurrence of the problem, except for purposes of localization.
25+ message : str
26+ # If an error can be associated to a particular point in the requested
27+ # GraphQL document, it should contain a list of locations.
28+ locations : List ["FormattedSourceLocation" ]
29+ # If an error can be associated to a particular field in the GraphQL result,
30+ # it _must_ contain an entry with the key `path` that details the path of
31+ # the response field which experienced the error. This allows clients to
32+ # identify whether a null result is intentional or caused by a runtime error.
33+ path : List [Union [str , int ]]
34+ # Reserved for implementors to extend the protocol however they see fit,
35+ # and hence there are no additional restrictions on its contents.
36+ extensions : Dict [str , Any ]
1037
1138
1239class GraphQLError (Exception ):
@@ -186,23 +213,21 @@ def __ne__(self, other: Any) -> bool:
186213 return not self == other
187214
188215 @property
189- def formatted (self ) -> Dict [ str , Any ] :
216+ def formatted (self ) -> GraphQLFormattedError :
190217 """Get error formatted according to the specification.
191218
192219 Given a GraphQLError, format it according to the rules described by the
193220 "Response Format, Errors" section of the GraphQL Specification.
194221 """
195- formatted : Dict [str , Any ] = dict ( # noqa: E701 (pycqa/flake8#394)
196- message = self .message or "An unknown error occurred." ,
197- locations = (
198- [location .formatted for location in self .locations ]
199- if self .locations is not None
200- else None
201- ),
202- path = self .path ,
203- )
222+ formatted : GraphQLFormattedError = {
223+ "message" : self .message or "An unknown error occurred." ,
224+ }
225+ if self .locations is not None :
226+ formatted ["locations" ] = [location .formatted for location in self .locations ]
227+ if self .path is not None :
228+ formatted ["path" ] = self .path
204229 if self .extensions :
205- formatted . update ( extensions = self .extensions )
230+ formatted [ " extensions" ] = self .extensions
206231 return formatted
207232
208233
@@ -219,7 +244,7 @@ def print_error(error: GraphQLError) -> str:
219244 return str (error )
220245
221246
222- def format_error (error : GraphQLError ) -> Dict [ str , Any ] :
247+ def format_error (error : GraphQLError ) -> GraphQLFormattedError :
223248 """Format a GraphQL error.
224249
225250 Given a GraphQLError, format it according to the rules described by the "Response
0 commit comments