Repository: planetlabs/planet-client-python
Pull request #568 (2022-05-26 19:14:11)

Search quick limit test #561


Patch:
diff --git a/planet/cli/data.py b/planet/cli/data.py
index d9a33a2..ec71611 100644
--- a/planet/cli/data.py
+++ b/planet/cli/data.py
@@ -92,10 +92,10 @@ async def search_quick(ctx, item_types, filter, name, limit, pretty):
     parameter will be applied to the stored quick search. This function
     outputs a series of GeoJSON descriptions, one for each of the returned
     items. The limit on the number of output items can be controlled using
-    the "--limit" option, which defaults to 100. If "--limit" is set to zero,
-    no limit is applied and all results (a potentially large number) are
-    returned. The output can also be optionally pretty-printed using
-    "--pretty".
+    the "--limit" option, which defaults to 100 if limit is set to None or
+    if the option is not used at all. If "--limit" is set to zero, no limit
+    is applied and all results (a potentially large number) are returned.
+    The output can also be optionally pretty-printed using "--pretty".
     """
     async with data_client(ctx) as cl:
         items = await cl.quick_search(name=name,
diff --git a/planet/clients/data.py b/planet/clients/data.py
index 4a244a0..a7b96ec 100644
--- a/planet/clients/data.py
+++ b/planet/clients/data.py
@@ -85,12 +85,14 @@ class DataClient:
         """
         return await self._session.request(request)
 
-    async def quick_search(self,
-                           item_types: typing.List[str],
-                           search_filter: dict,
-                           name: str = None,
-                           sort: str = None,
-                           limit: int = None) -> typing.AsyncIterator[dict]:
+    async def quick_search(
+            self,
+            item_types: typing.List[str],
+            search_filter: dict,
+            name: str = None,
+            sort: str = None,
+            limit: typing.Union[int,
+                                None] = 100) -> typing.AsyncIterator[dict]:
         """Execute a quick search.
 
         Quick searches are saved for a short period of time (~month). The
@@ -139,6 +141,10 @@ class DataClient:
         """
         url = f'{self._base_url}/quick-search'
 
+        # Set no limit
+        if limit == 0:
+            limit = None
+
         # TODO: validate item_types
         request_json = {'filter': search_filter, 'item_types': item_types}
         if name:


Test patch:
diff --git a/tests/integration/conftest.py b/tests/integration/conftest.py
index 378cb04..852131b 100644
--- a/tests/integration/conftest.py
+++ b/tests/integration/conftest.py
@@ -35,3 +35,14 @@ def order_descriptions(order_description):
     order3 = copy.deepcopy(order_description)
     order3['id'] = 'oid3'
     return [order1, order2, order3]
+
+
+@pytest.fixture
+def search_results(search_result):
+    result1 = search_result
+    result1['id'] = 'id1'
+    result2 = copy.deepcopy(search_result)
+    result2['id'] = 'id2'
+    result3 = copy.deepcopy(search_result)
+    result3['id'] = 'id3'
+    return [result1, result2, result3]
diff --git a/tests/integration/test_data_cli.py b/tests/integration/test_data_cli.py
index 4155bae..58e4b1f 100644
--- a/tests/integration/test_data_cli.py
+++ b/tests/integration/test_data_cli.py
@@ -81,6 +81,52 @@ def test_data_search_quick_filter_success(invoke, item_types):
     assert len(result.output.strip().split('\n')) == 1  # we have 1 feature
 
 
+@respx.mock
+@pytest.mark.parametrize("limit,limited_list_length", [(None, 100), (0, 102),
+                                                       (1, 1)])
+def test_data_search_quick_limit(invoke,
+                                 search_results,
+                                 limit,
+                                 limited_list_length):
+    """Test for planet data search_quick limit option. If no value is specified,
+    make sure the result contains at most 100 entries."""
+    filter = {
+        "type": "DateRangeFilter",
+        "field_name": "acquired",
+        "config": {
+            "gt": "2019-12-31T00:00:00Z", "lte": "2020-01-31T00:00:00Z"
+        }
+    }
+    item_types = 'SkySatCollect'
+
+    # Creating 102 (3x34) search results
+    long_search_results = search_results * 34
+
+    all_results = {}
+    for x in range(1, len(long_search_results) + 1):
+        all_results["result{0}".format(x)] = long_search_results[x - 1]
+
+    page1_response = {
+        "_links": {
+            "_self": "string1", "assets": "string2", "thumbnail": "string3"
+        },
+        "features": [
+            all_results[f'result{num}']
+            for num in range(1, limited_list_length + 1)
+        ]
+    }
+    mock_resp = httpx.Response(HTTPStatus.OK, json=page1_response)
+
+    respx.post(TEST_QUICKSEARCH_URL).return_value = mock_resp
+
+    runner = CliRunner()
+    result = invoke(
+        ["search-quick", item_types, json.dumps(filter), "--limit", limit],
+        runner=runner)
+    assert result.exit_code == 0
+    assert result.output.count('"id"') == limited_list_length
+
+
 @respx.mock
 @pytest.mark.asyncio
 @pytest.mark.parametrize("filter", ['{1:1}', '{"foo"}'])