From 48efa5b1ad6ff140d158b4786001251746027104 Mon Sep 17 00:00:00 2001 From: Alexandre Lavigne Date: Sun, 8 Sep 2024 18:46:32 +0200 Subject: [PATCH] better handler API error parsing. Possibly we encountered an error while parsing the API error JSON, like connection closes early etc and the received JSON is invalid. Better handle such scenario and build a valid error Dict to keep the exception stack flow running and raise this message to the application. extract the returned text so if we any bit of valid information at least we can pass that to the application. This could be helpfull to if we add calls to the API made for web browser that returns HTML error message, it will fail to decode the recieved error and raise a proper error. closes #1504 Signed-off-by: Alexandre Lavigne (cherry picked from commit db59084b59e4248b4d4db6891cb06cacd61328af) --- gspread/exceptions.py | 16 +++++++++++++++- 1 file changed, 15 insertions(+), 1 deletion(-) diff --git a/gspread/exceptions.py b/gspread/exceptions.py index 4701ebdf7..c22be15c0 100644 --- a/gspread/exceptions.py +++ b/gspread/exceptions.py @@ -9,6 +9,7 @@ from typing import Any, Dict, Mapping, Optional, Union from requests import Response +from requests.exceptions import JSONDecodeError class UnSupportedExportFormat(Exception): @@ -40,7 +41,20 @@ class APIError(GSpreadException): such as when we attempt to retrieve things that don't exist.""" def __init__(self, response: Response): - super().__init__(self._extract_error(response)) + try: + error = response.json()["error"] + except JSONDecodeError: + # in case we failed to parse the error from the API + # build an empty error object to notify the caller + # and keep the exception raise flow running + + error = { + "code": -1, + "message": response.text, + "status": "invalid JSON", + } + + super().__init__(error) self.response: Response = response self.error: Mapping[str, Any] = response.json()["error"] self.code: int = self.error["code"]