22import uuid
33from datetime import datetime , timedelta
44
5+ import pytest
6+
57from ..conftest import create_collection , create_item
68
79ROUTES = {
3133}
3234
3335
36+ @pytest .mark .asyncio
3437async def test_post_search_content_type (app_client , ctx ):
3538 params = {"limit" : 1 }
3639 resp = await app_client .post ("/search" , json = params )
3740 assert resp .headers ["content-type" ] == "application/geo+json"
3841
3942
43+ @pytest .mark .asyncio
4044async def test_get_search_content_type (app_client , ctx ):
4145 resp = await app_client .get ("/search" )
4246 assert resp .headers ["content-type" ] == "application/geo+json"
4347
4448
49+ @pytest .mark .asyncio
4550async def test_api_headers (app_client ):
4651 resp = await app_client .get ("/api" )
4752 assert (
@@ -50,11 +55,13 @@ async def test_api_headers(app_client):
5055 assert resp .status_code == 200
5156
5257
58+ @pytest .mark .asyncio
5359async def test_router (app ):
5460 api_routes = set ([f"{ list (route .methods )[0 ]} { route .path } " for route in app .routes ])
5561 assert len (api_routes - ROUTES ) == 0
5662
5763
64+ @pytest .mark .asyncio
5865async def test_app_transaction_extension (app_client , ctx ):
5966 item = copy .deepcopy (ctx .item )
6067 item ["id" ] = str (uuid .uuid4 ())
@@ -64,6 +71,7 @@ async def test_app_transaction_extension(app_client, ctx):
6471 await app_client .delete (f"/collections/{ item ['collection' ]} /items/{ item ['id' ]} " )
6572
6673
74+ @pytest .mark .asyncio
6775async def test_app_search_response (app_client , ctx ):
6876 resp = await app_client .get ("/search" , params = {"ids" : ["test-item" ]})
6977 assert resp .status_code == 200
@@ -75,6 +83,7 @@ async def test_app_search_response(app_client, ctx):
7583 assert resp_json .get ("stac_extensions" ) is None
7684
7785
86+ @pytest .mark .asyncio
7887async def test_app_context_extension (app_client , ctx , txn_client ):
7988 test_item = ctx .item
8089 test_item ["id" ] = "test-item-2"
@@ -108,13 +117,15 @@ async def test_app_context_extension(app_client, ctx, txn_client):
108117 assert matched == 1
109118
110119
120+ @pytest .mark .asyncio
111121async def test_app_fields_extension (app_client , ctx , txn_client ):
112122 resp = await app_client .get ("/search" , params = {"collections" : ["test-collection" ]})
113123 assert resp .status_code == 200
114124 resp_json = resp .json ()
115125 assert list (resp_json ["features" ][0 ]["properties" ]) == ["datetime" ]
116126
117127
128+ @pytest .mark .asyncio
118129async def test_app_fields_extension_query (app_client , ctx , txn_client ):
119130 resp = await app_client .post (
120131 "/search" ,
@@ -128,6 +139,7 @@ async def test_app_fields_extension_query(app_client, ctx, txn_client):
128139 assert list (resp_json ["features" ][0 ]["properties" ]) == ["datetime" , "proj:epsg" ]
129140
130141
142+ @pytest .mark .asyncio
131143async def test_app_fields_extension_no_properties_get (app_client , ctx , txn_client ):
132144 resp = await app_client .get (
133145 "/search" , params = {"collections" : ["test-collection" ], "fields" : "-properties" }
@@ -137,6 +149,7 @@ async def test_app_fields_extension_no_properties_get(app_client, ctx, txn_clien
137149 assert "properties" not in resp_json ["features" ][0 ]
138150
139151
152+ @pytest .mark .asyncio
140153async def test_app_fields_extension_no_properties_post (app_client , ctx , txn_client ):
141154 resp = await app_client .post (
142155 "/search" ,
@@ -150,6 +163,7 @@ async def test_app_fields_extension_no_properties_post(app_client, ctx, txn_clie
150163 assert "properties" not in resp_json ["features" ][0 ]
151164
152165
166+ @pytest .mark .asyncio
153167async def test_app_fields_extension_return_all_properties (app_client , ctx , txn_client ):
154168 item = ctx .item
155169 resp = await app_client .get (
@@ -166,6 +180,7 @@ async def test_app_fields_extension_return_all_properties(app_client, ctx, txn_c
166180 assert feature ["properties" ][expected_prop ] == expected_value
167181
168182
183+ @pytest .mark .asyncio
169184async def test_app_query_extension_gt (app_client , ctx ):
170185 params = {"query" : {"proj:epsg" : {"gt" : ctx .item ["properties" ]["proj:epsg" ]}}}
171186 resp = await app_client .post ("/search" , json = params )
@@ -174,6 +189,7 @@ async def test_app_query_extension_gt(app_client, ctx):
174189 assert len (resp_json ["features" ]) == 0
175190
176191
192+ @pytest .mark .asyncio
177193async def test_app_query_extension_gte (app_client , ctx ):
178194 params = {"query" : {"proj:epsg" : {"gte" : ctx .item ["properties" ]["proj:epsg" ]}}}
179195 resp = await app_client .post ("/search" , json = params )
@@ -182,21 +198,95 @@ async def test_app_query_extension_gte(app_client, ctx):
182198 assert len (resp .json ()["features" ]) == 1
183199
184200
201+ @pytest .mark .asyncio
185202async def test_app_query_extension_limit_lt0 (app_client ):
186203 assert (await app_client .post ("/search" , json = {"limit" : - 1 })).status_code == 400
187204
188205
206+ @pytest .mark .asyncio
189207async def test_app_query_extension_limit_gt10000 (app_client ):
190208 assert (await app_client .post ("/search" , json = {"limit" : 10001 })).status_code == 400
191209
192210
211+ @pytest .mark .asyncio
193212async def test_app_query_extension_limit_10000 (app_client ):
194213 params = {"limit" : 10000 }
195214 resp = await app_client .post ("/search" , json = params )
196215 assert resp .status_code == 200
197216
198217
199- async def test_app_sort_extension (app_client , txn_client , ctx ):
218+ @pytest .mark .asyncio
219+ async def test_app_sort_extension_get_asc (app_client , txn_client , ctx ):
220+ first_item = ctx .item
221+ item_date = datetime .strptime (
222+ first_item ["properties" ]["datetime" ], "%Y-%m-%dT%H:%M:%SZ"
223+ )
224+
225+ second_item = dict (first_item )
226+ second_item ["id" ] = "another-item"
227+ another_item_date = item_date - timedelta (days = 1 )
228+ second_item ["properties" ]["datetime" ] = another_item_date .strftime (
229+ "%Y-%m-%dT%H:%M:%SZ"
230+ )
231+ await create_item (txn_client , second_item )
232+
233+ resp = await app_client .get ("/search?sortby=+properties.datetime" )
234+ assert resp .status_code == 200
235+ resp_json = resp .json ()
236+ assert resp_json ["features" ][1 ]["id" ] == first_item ["id" ]
237+ assert resp_json ["features" ][0 ]["id" ] == second_item ["id" ]
238+
239+
240+ @pytest .mark .asyncio
241+ async def test_app_sort_extension_get_desc (app_client , txn_client , ctx ):
242+ first_item = ctx .item
243+ item_date = datetime .strptime (
244+ first_item ["properties" ]["datetime" ], "%Y-%m-%dT%H:%M:%SZ"
245+ )
246+
247+ second_item = dict (first_item )
248+ second_item ["id" ] = "another-item"
249+ another_item_date = item_date - timedelta (days = 1 )
250+ second_item ["properties" ]["datetime" ] = another_item_date .strftime (
251+ "%Y-%m-%dT%H:%M:%SZ"
252+ )
253+ await create_item (txn_client , second_item )
254+
255+ resp = await app_client .get ("/search?sortby=-properties.datetime" )
256+ assert resp .status_code == 200
257+ resp_json = resp .json ()
258+ assert resp_json ["features" ][0 ]["id" ] == first_item ["id" ]
259+ assert resp_json ["features" ][1 ]["id" ] == second_item ["id" ]
260+
261+
262+ @pytest .mark .asyncio
263+ async def test_app_sort_extension_post_asc (app_client , txn_client , ctx ):
264+ first_item = ctx .item
265+ item_date = datetime .strptime (
266+ first_item ["properties" ]["datetime" ], "%Y-%m-%dT%H:%M:%SZ"
267+ )
268+
269+ second_item = dict (first_item )
270+ second_item ["id" ] = "another-item"
271+ another_item_date = item_date - timedelta (days = 1 )
272+ second_item ["properties" ]["datetime" ] = another_item_date .strftime (
273+ "%Y-%m-%dT%H:%M:%SZ"
274+ )
275+ await create_item (txn_client , second_item )
276+
277+ params = {
278+ "collections" : [first_item ["collection" ]],
279+ "sortby" : [{"field" : "properties.datetime" , "direction" : "asc" }],
280+ }
281+ resp = await app_client .post ("/search" , json = params )
282+ assert resp .status_code == 200
283+ resp_json = resp .json ()
284+ assert resp_json ["features" ][1 ]["id" ] == first_item ["id" ]
285+ assert resp_json ["features" ][0 ]["id" ] == second_item ["id" ]
286+
287+
288+ @pytest .mark .asyncio
289+ async def test_app_sort_extension_post_desc (app_client , txn_client , ctx ):
200290 first_item = ctx .item
201291 item_date = datetime .strptime (
202292 first_item ["properties" ]["datetime" ], "%Y-%m-%dT%H:%M:%SZ"
@@ -221,6 +311,7 @@ async def test_app_sort_extension(app_client, txn_client, ctx):
221311 assert resp_json ["features" ][1 ]["id" ] == second_item ["id" ]
222312
223313
314+ @pytest .mark .asyncio
224315async def test_search_invalid_date (app_client , ctx ):
225316 params = {
226317 "datetime" : "2020-XX-01/2020-10-30" ,
@@ -231,6 +322,7 @@ async def test_search_invalid_date(app_client, ctx):
231322 assert resp .status_code == 400
232323
233324
325+ @pytest .mark .asyncio
234326async def test_search_point_intersects (app_client , ctx ):
235327 point = [150.04 , - 33.14 ]
236328 intersects = {"type" : "Point" , "coordinates" : point }
@@ -246,6 +338,7 @@ async def test_search_point_intersects(app_client, ctx):
246338 assert len (resp_json ["features" ]) == 1
247339
248340
341+ @pytest .mark .asyncio
249342async def test_search_point_does_not_intersect (app_client , ctx ):
250343 point = [15.04 , - 3.14 ]
251344 intersects = {"type" : "Point" , "coordinates" : point }
@@ -261,6 +354,7 @@ async def test_search_point_does_not_intersect(app_client, ctx):
261354 assert len (resp_json ["features" ]) == 0
262355
263356
357+ @pytest .mark .asyncio
264358async def test_datetime_non_interval (app_client , ctx ):
265359 dt_formats = [
266360 "2020-02-12T12:30:22+00:00" ,
@@ -282,6 +376,7 @@ async def test_datetime_non_interval(app_client, ctx):
282376 assert resp_json ["features" ][0 ]["properties" ]["datetime" ][0 :19 ] == dt [0 :19 ]
283377
284378
379+ @pytest .mark .asyncio
285380async def test_bbox_3d (app_client , ctx ):
286381 australia_bbox = [106.343365 , - 47.199523 , 0.1 , 168.218365 , - 19.437288 , 0.1 ]
287382 params = {
@@ -294,6 +389,7 @@ async def test_bbox_3d(app_client, ctx):
294389 assert len (resp_json ["features" ]) == 1
295390
296391
392+ @pytest .mark .asyncio
297393async def test_search_line_string_intersects (app_client , ctx ):
298394 line = [[150.04 , - 33.14 ], [150.22 , - 33.89 ]]
299395 intersects = {"type" : "LineString" , "coordinates" : line }
0 commit comments