diff --git a/CHANGELOG.rst b/CHANGELOG.rst index 7b12f76..a13fba8 100644 --- a/CHANGELOG.rst +++ b/CHANGELOG.rst @@ -2,11 +2,19 @@ Changelog ========= +0.1.17 (2026-06-08) +------------------- + +* Add ``APINotFound`` exception and 404 handling in ``_make_request``. + 0.1.16 (2026-06-02) ------------------- +* Add support for QUADS server polling/status API. * Add move status API methods: ``get_all_move_status``, ``get_move_status``, ``start_move_batch``, ``update_move_status``. +* Align with ``MoveStatus`` enum refactor and simplified ``MoveProgress`` DB + structure on the server side. 0.0.0 (2025-01-07) ------------------ diff --git a/rpm/quads-lib.spec b/rpm/quads-lib.spec index c2dc9f3..fa7b3fa 100644 --- a/rpm/quads-lib.spec +++ b/rpm/quads-lib.spec @@ -12,7 +12,7 @@ %define name quads-lib %define reponame python-quads-lib %define branch development -%define version 0.1.16 +%define version 0.1.17 %define build_timestamp %{lua: print(os.date("%Y%m%d"))} Summary: Python client library for interacting with the QUADS API diff --git a/setup.py b/setup.py index 821bf44..12ee05d 100755 --- a/setup.py +++ b/setup.py @@ -13,7 +13,7 @@ def read(*names, **kwargs): setup( name="quads-lib", - version="0.1.16", + version="0.1.17", license="LGPL-3.0-only", description="Python client library for interacting with the QUADS API", long_description="{}\n{}".format( diff --git a/src/quads_lib/__init__.py b/src/quads_lib/__init__.py index 38252f5..901f216 100644 --- a/src/quads_lib/__init__.py +++ b/src/quads_lib/__init__.py @@ -1,4 +1,4 @@ -__version__ = "0.1.16" +__version__ = "0.1.17" from .quads import QuadsApi diff --git a/src/quads_lib/base.py b/src/quads_lib/base.py index 12f1709..a993197 100644 --- a/src/quads_lib/base.py +++ b/src/quads_lib/base.py @@ -9,6 +9,7 @@ from requests.auth import HTTPBasicAuth from quads_lib.exceptions import APIBadRequest +from quads_lib.exceptions import APINotFound from quads_lib.exceptions import APIServerException @@ -75,6 +76,12 @@ def _make_request(self, method: str, endpoint: str, data: Optional[dict] = None) ) if _response.status_code == 500: raise APIServerException("Check the flask server logs") + if _response.status_code == 404: + try: + response_json = _response.json() + except JSONDecodeError as e: + raise APINotFound("Resource not found") from e + raise APINotFound(response_json.get("message", "Resource not found")) if _response.status_code == 400: try: response_json = _response.json() diff --git a/src/quads_lib/exceptions.py b/src/quads_lib/exceptions.py index 455fd77..9a98293 100644 --- a/src/quads_lib/exceptions.py +++ b/src/quads_lib/exceptions.py @@ -4,3 +4,7 @@ class APIServerException(Exception): class APIBadRequest(Exception): pass + + +class APINotFound(Exception): + pass diff --git a/tests/test_quads.py b/tests/test_quads.py index 9bedc57..33c79c5 100644 --- a/tests/test_quads.py +++ b/tests/test_quads.py @@ -7,6 +7,7 @@ from quads_lib.base import QuadsBase from quads_lib.exceptions import APIBadRequest +from quads_lib.exceptions import APINotFound from quads_lib.exceptions import APIServerException from quads_lib.quads import QuadsApi @@ -1857,6 +1858,26 @@ def test_get_move_status_error(self, mock_get): with pytest.raises(APIServerException, match="Check the flask server logs"): self.api.get_move_status("host1") + @patch("requests.Session.request") + def test_get_move_status_not_found(self, mock_get): + mock_response = Mock() + mock_response.status_code = 404 + mock_response.json.return_value = {"message": "Resource not found"} + mock_get.return_value = mock_response + + with pytest.raises(APINotFound, match="Resource not found"): + self.api.get_move_status("host1") + + @patch("requests.Session.request") + def test_get_all_move_status_not_found(self, mock_get): + mock_response = Mock() + mock_response.status_code = 404 + mock_response.json.side_effect = JSONDecodeError("", "", 0) + mock_get.return_value = mock_response + + with pytest.raises(APINotFound, match="Resource not found"): + self.api.get_all_move_status() + @patch("requests.Session.request") def test_get_version(self, mock_get): expected_response = {"version": "1.0.0", "api_version": "2.0"}