Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: add new storage error class #313

Merged
merged 1 commit into from
Nov 22, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
14 changes: 7 additions & 7 deletions storage3/_async/bucket.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,10 +2,11 @@

from typing import Any, Optional

from httpx import HTTPError, Response
from httpx import HTTPStatusError, Response

from ..exceptions import StorageApiError
from ..types import CreateOrUpdateBucketOptions, RequestMethod
from ..utils import AsyncClient, StorageException
from ..utils import AsyncClient
from .file_api import AsyncBucket

__all__ = ["AsyncStorageBucketAPI"]
Expand All @@ -23,13 +24,12 @@ async def _request(
url: str,
json: Optional[dict[Any, Any]] = None,
) -> Response:
response = await self._client.request(method, url, json=json)
try:
response = await self._client.request(method, url, json=json)
response.raise_for_status()
except HTTPError:
raise StorageException(
{**response.json(), "statusCode": response.status_code}
)
except HTTPStatusError as exc:
resp = exc.response.json()
raise StorageApiError(resp["message"], resp["error"], resp["statusCode"])

return response

Expand Down
13 changes: 5 additions & 8 deletions storage3/_async/file_api.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,13 +3,13 @@
import urllib.parse
from dataclasses import dataclass, field
from io import BufferedReader, FileIO
from json import JSONDecodeError
from pathlib import Path
from typing import Any, Literal, Optional, Union, cast

from httpx import HTTPError, Response
from httpx import HTTPStatusError, Response

from ..constants import DEFAULT_FILE_OPTIONS, DEFAULT_SEARCH_OPTIONS
from ..exceptions import StorageApiError
from ..types import (
BaseBucket,
CreateSignedURLsOptions,
Expand Down Expand Up @@ -47,12 +47,9 @@ async def _request(
method, url, headers=headers or {}, json=json, files=files, **kwargs
)
response.raise_for_status()
except HTTPError:
try:
resp = response.json()
raise StorageException({**resp, "statusCode": response.status_code})
except JSONDecodeError:
raise StorageException({"statusCode": response.status_code})
except HTTPStatusError as exc:
resp = exc.response.json()
raise StorageApiError(resp["message"], resp["error"], resp["statusCode"])

return response

Expand Down
14 changes: 7 additions & 7 deletions storage3/_sync/bucket.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,10 +2,11 @@

from typing import Any, Optional

from httpx import HTTPError, Response
from httpx import HTTPStatusError, Response

from ..exceptions import StorageApiError
from ..types import CreateOrUpdateBucketOptions, RequestMethod
from ..utils import StorageException, SyncClient
from ..utils import SyncClient
from .file_api import SyncBucket

__all__ = ["SyncStorageBucketAPI"]
Expand All @@ -23,13 +24,12 @@ def _request(
url: str,
json: Optional[dict[Any, Any]] = None,
) -> Response:
response = self._client.request(method, url, json=json)
try:
response = self._client.request(method, url, json=json)
response.raise_for_status()
except HTTPError:
raise StorageException(
{**response.json(), "statusCode": response.status_code}
)
except HTTPStatusError as exc:
resp = exc.response.json()
raise StorageApiError(resp["message"], resp["error"], resp["statusCode"])

return response

Expand Down
13 changes: 5 additions & 8 deletions storage3/_sync/file_api.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,13 +3,13 @@
import urllib.parse
from dataclasses import dataclass, field
from io import BufferedReader, FileIO
from json import JSONDecodeError
from pathlib import Path
from typing import Any, Literal, Optional, Union, cast

from httpx import HTTPError, Response
from httpx import HTTPStatusError, Response

from ..constants import DEFAULT_FILE_OPTIONS, DEFAULT_SEARCH_OPTIONS
from ..exceptions import StorageApiError
from ..types import (
BaseBucket,
CreateSignedURLsOptions,
Expand Down Expand Up @@ -47,12 +47,9 @@ def _request(
method, url, headers=headers or {}, json=json, files=files, **kwargs
)
response.raise_for_status()
except HTTPError:
try:
resp = response.json()
raise StorageException({**resp, "statusCode": response.status_code})
except JSONDecodeError:
raise StorageException({"statusCode": response.status_code})
except HTTPStatusError as exc:
resp = exc.response.json()
raise StorageApiError(resp["message"], resp["error"], resp["statusCode"])

return response

Expand Down
33 changes: 33 additions & 0 deletions storage3/exceptions.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
from typing import TypedDict

from .utils import StorageException


class StorageApiErrorDict(TypedDict):
name: str
message: str
status: int


class StorageApiError(StorageException):
"""Error raised when an operation on the storage API fails."""

def __init__(self, message: str, code: str, status: int) -> None:
error_message = "{{'statusCode': {}, 'error': {}, 'message': {}}}".format(
status,
code,
message,
)
super().__init__(error_message)
self.name = "StorageApiError"
self.message = message
self.code = code
self.status = status

def to_dict(self) -> StorageApiErrorDict:
return {
"name": self.name,
"code": self.code,
"message": self.message,
"status": self.status,
}