From 70519231aaf16dedacb12319ae97e7c6c757ad45 Mon Sep 17 00:00:00 2001 From: uriyay Date: Thu, 21 Mar 2024 10:06:43 +0200 Subject: [PATCH 1/3] added support in requests.Session --- python_graphql_client/graphql_client.py | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/python_graphql_client/graphql_client.py b/python_graphql_client/graphql_client.py index 1d3d104..6d5ccca 100644 --- a/python_graphql_client/graphql_client.py +++ b/python_graphql_client/graphql_client.py @@ -5,6 +5,7 @@ import aiohttp import requests +from requests import Session import websockets @@ -37,6 +38,7 @@ def execute( variables: dict = None, operation_name: str = None, headers: dict = {}, + session: Session = None, **kwargs: Any, ): """Make synchronous request to graphQL server.""" @@ -44,7 +46,10 @@ def execute( query=query, variables=variables, operation_name=operation_name ) - result = requests.post( + if session is None: + session = Session() + + result = session.post( self.endpoint, json=request_body, headers={**self.headers, **headers}, From 6d1b3050474458566d0290a8d3d77e437ef5794e Mon Sep 17 00:00:00 2001 From: uriyay Date: Thu, 21 Mar 2024 21:23:59 +0200 Subject: [PATCH 2/3] client.execute() will use requests.post if session object is not given. added tests for testing client.execute() with a given session object --- python_graphql_client/graphql_client.py | 9 +- tests/test_graphql_client.py | 114 ++++++++++++++++++++++++ 2 files changed, 119 insertions(+), 4 deletions(-) diff --git a/python_graphql_client/graphql_client.py b/python_graphql_client/graphql_client.py index 6d5ccca..2c85a0a 100644 --- a/python_graphql_client/graphql_client.py +++ b/python_graphql_client/graphql_client.py @@ -5,8 +5,8 @@ import aiohttp import requests -from requests import Session import websockets +from requests import Session class GraphqlClient: @@ -46,10 +46,11 @@ def execute( query=query, variables=variables, operation_name=operation_name ) - if session is None: - session = Session() + post_method = requests.post + if session: + post_method = session.post - result = session.post( + result = post_method( self.endpoint, json=request_body, headers={**self.headers, **headers}, diff --git a/tests/test_graphql_client.py b/tests/test_graphql_client.py index 4a44207..2731f9b 100644 --- a/tests/test_graphql_client.py +++ b/tests/test_graphql_client.py @@ -145,6 +145,120 @@ def test_execute_query_with_operation_name(self, post_mock): ) +class TestGraphqlClientExecuteSession(TestCase): + """Test cases for synchronous graphql request function using a Session object.""" + + def test_execute_basic_query(self): + """Sends a graphql POST request to an endpoint.""" + session_mock = MagicMock() + client = GraphqlClient(endpoint="http://www.test-api.com/") + query = """ + { + tests { + status + } + } + """ + client.execute(query, session=session_mock) + + session_mock.post.assert_called_once_with( + "http://www.test-api.com/", json={"query": query}, headers={} + ) + + def test_execute_query_with_variables(self): + """Sends a graphql POST request with variables.""" + session_mock = MagicMock() + client = GraphqlClient(endpoint="http://www.test-api.com/") + query = "" + variables = {"id": 123} + client.execute(query, variables, session=session_mock) + + session_mock.post.assert_called_once_with( + "http://www.test-api.com/", + json={"query": query, "variables": variables}, + headers={}, + ) + + def test_raises_http_errors_as_exceptions(self): + """Raises an exception if an http error code is returned in the response.""" + session_mock = MagicMock() + response_mock = MagicMock() + response_mock.raise_for_status.side_effect = HTTPError() + session_mock.post.return_value = response_mock + + client = GraphqlClient(endpoint="http://www.test-api.com/") + + with self.assertRaises(HTTPError): + client.execute(query="", session=session_mock) + + def test_execute_query_with_headers(self): + """Sends a graphql POST request with headers.""" + session_mock = MagicMock() + client = GraphqlClient( + endpoint="http://www.test-api.com/", + headers={"Content-Type": "application/json", "Existing": "123"}, + ) + query = "" + client.execute(query=query, + headers={"Existing": "456", "New": "foo"}, + session=session_mock) + + session_mock.post.assert_called_once_with( + "http://www.test-api.com/", + json={"query": query}, + headers={ + "Content-Type": "application/json", + "Existing": "456", + "New": "foo", + }, + ) + + def test_execute_query_with_options(self): + """Sends a graphql POST request with headers.""" + session_mock = MagicMock() + auth = HTTPBasicAuth("fake@example.com", "not_a_real_password") + client = GraphqlClient( + endpoint="http://www.test-api.com/", + auth=auth, + ) + query = "" + client.execute(query=query, verify=False, session=session_mock) + + session_mock.post.assert_called_once_with( + "http://www.test-api.com/", + json={"query": query}, + headers={}, + auth=HTTPBasicAuth("fake@example.com", "not_a_real_password"), + verify=False, + ) + + def test_execute_query_with_operation_name(self): + """Sends a graphql POST request with the operationName key set.""" + session_mock = MagicMock() + client = GraphqlClient(endpoint="http://www.test-api.com/") + query = """ + query firstQuery { + test { + status + } + } + + query secondQuery { + test { + status + } + } + """ + operation_name = "firstQuery" + client.execute(query, operation_name=operation_name, session=session_mock) + + session_mock.post.assert_called_once_with( + "http://www.test-api.com/", + json={"query": query, "operationName": operation_name}, + headers={}, + ) + + class TestGraphqlClientExecuteAsync(IsolatedAsyncioTestCase): """Test cases for the asynchronous graphQL request function.""" From c230ae74dd7032529505ad1a5f791f67288fdf36 Mon Sep 17 00:00:00 2001 From: uriyay Date: Sun, 7 Apr 2024 11:23:34 +0300 Subject: [PATCH 3/3] Update tests/test_graphql_client.py Co-authored-by: Justin Krinke --- tests/test_graphql_client.py | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/tests/test_graphql_client.py b/tests/test_graphql_client.py index 2731f9b..d02b07a 100644 --- a/tests/test_graphql_client.py +++ b/tests/test_graphql_client.py @@ -199,9 +199,9 @@ def test_execute_query_with_headers(self): headers={"Content-Type": "application/json", "Existing": "123"}, ) query = "" - client.execute(query=query, - headers={"Existing": "456", "New": "foo"}, - session=session_mock) + client.execute( + query=query, headers={"Existing": "456", "New": "foo"}, session=session_mock + ) session_mock.post.assert_called_once_with( "http://www.test-api.com/",