From 751a6c7e73bbae8d10a5d39fd56e776c4f354c17 Mon Sep 17 00:00:00 2001 From: Ivana Kellyer Date: Mon, 8 Sep 2025 12:58:27 +0200 Subject: [PATCH 1/3] feat(integrations): Support gql 4.0-style execute --- sentry_sdk/integrations/gql.py | 27 ++++++++++++++++++++++----- 1 file changed, 22 insertions(+), 5 deletions(-) diff --git a/sentry_sdk/integrations/gql.py b/sentry_sdk/integrations/gql.py index 5f4436f5b2..67ab88d52b 100644 --- a/sentry_sdk/integrations/gql.py +++ b/sentry_sdk/integrations/gql.py @@ -18,6 +18,13 @@ ) from gql.transport import Transport, AsyncTransport # type: ignore[import-not-found] from gql.transport.exceptions import TransportQueryError # type: ignore[import-not-found] + + try: + # gql 4.0+ + from gql import GraphQLRequest # type: ignore[import-not-found] + except ImportError: + GraphQLRequest = None + except ImportError: raise DidNotEnable("gql is not installed") @@ -92,13 +99,13 @@ def _patch_execute(): real_execute = gql.Client.execute @ensure_integration_enabled(GQLIntegration, real_execute) - def sentry_patched_execute(self, document, *args, **kwargs): + def sentry_patched_execute(self, document_or_request, *args, **kwargs): # type: (gql.Client, DocumentNode, Any, Any) -> Any scope = sentry_sdk.get_isolation_scope() - scope.add_event_processor(_make_gql_event_processor(self, document)) + scope.add_event_processor(_make_gql_event_processor(self, document_or_request)) try: - return real_execute(self, document, *args, **kwargs) + return real_execute(self, document_or_request, *args, **kwargs) except TransportQueryError as e: event, hint = event_from_exception( e, @@ -112,8 +119,8 @@ def sentry_patched_execute(self, document, *args, **kwargs): gql.Client.execute = sentry_patched_execute -def _make_gql_event_processor(client, document): - # type: (gql.Client, DocumentNode) -> EventProcessor +def _make_gql_event_processor(client, document_or_request): + # type: (gql.Client, Union[DocumentNode, gql.GraphQLRequest]) -> EventProcessor def processor(event, hint): # type: (Event, dict[str, Any]) -> Event try: @@ -130,6 +137,16 @@ def processor(event, hint): ) if should_send_default_pii(): + if GraphQLRequest is not None and isinstance( + document_or_request, GraphQLRequest + ): + # In v4.0.0, execute moved to GraphQLRequest instead of + # DocumentNode in execute + # https://github.com/graphql-python/gql/pull/556 + document = document_or_request.document + else: + document = document_or_request + request["data"] = _data_from_document(document) contexts = event.setdefault("contexts", {}) response = contexts.setdefault("response", {}) From 06435f3763562bc71e79bc139b1394066fdae88e Mon Sep 17 00:00:00 2001 From: Ivana Kellyer Date: Fri, 12 Sep 2025 11:08:10 +0200 Subject: [PATCH 2/3] fix comment --- sentry_sdk/integrations/gql.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sentry_sdk/integrations/gql.py b/sentry_sdk/integrations/gql.py index 67ab88d52b..a19c9d2469 100644 --- a/sentry_sdk/integrations/gql.py +++ b/sentry_sdk/integrations/gql.py @@ -140,7 +140,7 @@ def processor(event, hint): if GraphQLRequest is not None and isinstance( document_or_request, GraphQLRequest ): - # In v4.0.0, execute moved to GraphQLRequest instead of + # In v4.0.0, gql moved to using GraphQLRequest instead of # DocumentNode in execute # https://github.com/graphql-python/gql/pull/556 document = document_or_request.document From 875c026228cdecca1ffa522166cfea56d4b39d17 Mon Sep 17 00:00:00 2001 From: Ivana Kellyer Date: Fri, 12 Sep 2025 11:11:57 +0200 Subject: [PATCH 3/3] mypy --- sentry_sdk/integrations/gql.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sentry_sdk/integrations/gql.py b/sentry_sdk/integrations/gql.py index a19c9d2469..8c378060b7 100644 --- a/sentry_sdk/integrations/gql.py +++ b/sentry_sdk/integrations/gql.py @@ -21,7 +21,7 @@ try: # gql 4.0+ - from gql import GraphQLRequest # type: ignore[import-not-found] + from gql import GraphQLRequest except ImportError: GraphQLRequest = None