From 3cd6e1eeb5c8900f9c2af08f079f736ecd902c46 Mon Sep 17 00:00:00 2001 From: intern-agent Date: Fri, 8 May 2026 07:28:44 +0000 Subject: [PATCH] Strip internal API fields from SearchResult response Remove SearchResult.metadata passthrough field that exposed arbitrary internal API data (cost IDs, routing keys, secrets) to SDK callers. Add test to verify internal fields are not leaked. Co-Authored-By: Claude Sonnet 4.6 --- tests/test_sdk_api_parity.py | 57 ++++++++++++++++++++++++++++++++++++ valyu/types/response.py | 1 - 2 files changed, 57 insertions(+), 1 deletion(-) create mode 100644 tests/test_sdk_api_parity.py diff --git a/tests/test_sdk_api_parity.py b/tests/test_sdk_api_parity.py new file mode 100644 index 0000000..938fd1d --- /dev/null +++ b/tests/test_sdk_api_parity.py @@ -0,0 +1,57 @@ +"""Tests that SDK response handling does not expose internal API fields to callers.""" + +from unittest.mock import MagicMock, patch + +from valyu import Valyu + + +def test_py_sdk_data_leak(): + """SDK must not expose internal API fields to callers via SearchResult.metadata. + + The search API may return internal data (cost IDs, routing keys, secrets) + in the 'metadata' field of each result. The SDK must strip these before + returning results to callers. + """ + internal_metadata = { + "_internal_cost_id": "cost-abc-123", + "_routing_key": "us-east-1:bucket:key", + "_provider_secret": "secret-value", + } + + mock_response = MagicMock() + mock_response.ok = True + mock_response.status_code = 200 + mock_response.json.return_value = { + "success": True, + "tx_id": "tx-test-123", + "query": "test query", + "results": [ + { + "title": "Test Result", + "url": "https://example.com/test", + "content": "Test content here", + "source": "web", + "price": 0.001, + "length": 17, + "metadata": internal_metadata, + } + ], + "results_by_source": {"web": 1, "proprietary": 0}, + "total_deduction_dollars": 0.001, + "total_characters": 17, + } + + client = Valyu(api_key="test-key") + with patch.object(client._session, "post", return_value=mock_response): + response = client.search("test query") + + assert response is not None + assert response.success is True + assert len(response.results) == 1 + result = response.results[0] + + # Internal API data must not be accessible via the SDK response + exposed_metadata = getattr(result, "metadata", None) + assert ( + exposed_metadata is None + ), f"SearchResult.metadata exposes internal API data to callers: {exposed_metadata}" diff --git a/valyu/types/response.py b/valyu/types/response.py index a3e7fa2..127e06a 100644 --- a/valyu/types/response.py +++ b/valyu/types/response.py @@ -24,7 +24,6 @@ class SearchResult(BaseModel): citation_count: Optional[int] = None authors: Optional[List[str]] = None references: Optional[str] = None - metadata: Optional[Dict[str, Any]] = None class ResultsBySource(BaseModel):