This is an automated email from the ASF dual-hosted git repository.

github-merge-queue[bot] pushed a commit to branch 
gh-readonly-queue/main/pr-4152-e6eb6a93b94c547a5f2b68f5eb68f64a44cc48af
in repository https://gitbox.apache.org/repos/asf/iceberg-python.git

commit 5becad1aefcc7de7767d2aa30cef07b48c61aff3
Author: Kevin Liu <[email protected]>
AuthorDate: Sun Oct 25 04:00:43 2026 +0000

    REST: Require metadata-location in view responses (#4152)
    
    Require metadata-location in REST view responses
    
    The REST spec marks metadata-location as required in LoadViewResult, and
    Java's LoadViewResponseParser rejects responses without it. Make
    ViewResponse.metadata_location required to match.
    
    Behavior change: create_view, load_view, and register_view now raise a
    pydantic ValidationError for non-compliant servers that omit
    metadata-location, instead of silently accepting the response.
    
    Co-authored-by: Copilot App <[email protected]>
---
 pyiceberg/catalog/rest/__init__.py |  2 +-
 tests/catalog/test_rest.py         | 14 ++++++++++++++
 2 files changed, 15 insertions(+), 1 deletion(-)

diff --git a/pyiceberg/catalog/rest/__init__.py 
b/pyiceberg/catalog/rest/__init__.py
index 97b2e2350..80f853f01 100644
--- a/pyiceberg/catalog/rest/__init__.py
+++ b/pyiceberg/catalog/rest/__init__.py
@@ -361,7 +361,7 @@ class LoadCredentialsResponse(IcebergBaseModel):
 
 
 class ViewResponse(IcebergBaseModel):
-    metadata_location: str | None = Field(alias="metadata-location", 
default=None)
+    metadata_location: str = Field(..., alias="metadata-location")
     metadata: ViewMetadata
     config: Properties = Field(default_factory=dict)
 
diff --git a/tests/catalog/test_rest.py b/tests/catalog/test_rest.py
index b1b46e467..e355a6873 100644
--- a/tests/catalog/test_rest.py
+++ b/tests/catalog/test_rest.py
@@ -26,6 +26,7 @@ from unittest import mock
 from urllib.parse import parse_qs, urlsplit
 
 import pytest
+from pydantic import ValidationError
 from requests import Request
 from requests.adapters import HTTPAdapter
 from requests.exceptions import HTTPError
@@ -1856,6 +1857,19 @@ def test_load_view_200(rest_mock: Mocker, 
example_view_metadata_rest_json: dict[
     assert actual.config == example_view_metadata_rest_json["config"]
 
 
+def test_load_view_missing_metadata_location(rest_mock: Mocker, 
example_view_metadata_rest_json: dict[str, Any]) -> None:
+    response = {k: v for k, v in example_view_metadata_rest_json.items() if k 
!= "metadata-location"}
+    rest_mock.get(
+        f"{TEST_URI}v1/namespaces/fokko/views/view",
+        json=response,
+        status_code=200,
+        request_headers=TEST_HEADERS,
+    )
+    catalog = RestCatalog("rest", uri=TEST_URI, token=TEST_TOKEN)
+    with pytest.raises(ValidationError, match="metadata-location"):
+        catalog.load_view(("fokko", "view"))
+
+
 def test_load_view_404(rest_mock: Mocker) -> None:
     rest_mock.get(
         f"{TEST_URI}v1/namespaces/fokko/views/non_existent_view",

Reply via email to