stac-fastapi.extensions 5.0.2__tar.gz → 5.0.3__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/PKG-INFO +1 -1
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/collection_search/request.py +16 -18
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/version.py +1 -1
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi.extensions.egg-info/PKG-INFO +1 -1
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/tests/test_collection_search.py +14 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/README.md +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/setup.cfg +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/setup.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/__init__.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/__init__.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/aggregation/__init__.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/aggregation/aggregation.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/aggregation/client.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/aggregation/request.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/aggregation/types.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/collection_search/__init__.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/collection_search/client.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/collection_search/collection_search.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/fields/__init__.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/fields/fields.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/fields/request.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/filter/__init__.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/filter/client.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/filter/filter.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/filter/request.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/free_text/__init__.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/free_text/free_text.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/free_text/request.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/pagination/__init__.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/pagination/offset_pagination.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/pagination/pagination.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/pagination/request.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/pagination/token_pagination.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/query/__init__.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/query/query.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/query/request.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/sort/__init__.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/sort/request.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/sort/sort.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/core/transaction.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/third_party/__init__.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/third_party/bulk_transactions.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi.extensions.egg-info/SOURCES.txt +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi.extensions.egg-info/dependency_links.txt +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi.extensions.egg-info/not-zip-safe +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi.extensions.egg-info/requires.txt +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi.extensions.egg-info/top_level.txt +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/tests/test_aggregation.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/tests/test_filter.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/tests/test_free_text.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/tests/test_pagination.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/tests/test_query.py +0 -0
- {stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/tests/test_transaction.py +0 -0
|
@@ -5,7 +5,7 @@ from typing import List, Optional, Tuple, cast
|
|
|
5
5
|
|
|
6
6
|
import attr
|
|
7
7
|
from fastapi import Query
|
|
8
|
-
from pydantic import BaseModel, Field, field_validator
|
|
8
|
+
from pydantic import BaseModel, Field, PrivateAttr, ValidationInfo, field_validator
|
|
9
9
|
from stac_pydantic.api.search import SearchDatetime
|
|
10
10
|
from stac_pydantic.shared import BBox
|
|
11
11
|
from typing_extensions import Annotated
|
|
@@ -64,8 +64,8 @@ Either a date-time or an interval, open or closed. Date and time expressions adh
|
|
|
64
64
|
|
|
65
65
|
# Private properties to store the parsed datetime values.
|
|
66
66
|
# Not part of the model schema.
|
|
67
|
-
_start_date: Optional[dt] = None
|
|
68
|
-
_end_date: Optional[dt] = None
|
|
67
|
+
_start_date: Optional[dt] = PrivateAttr(default=None)
|
|
68
|
+
_end_date: Optional[dt] = PrivateAttr(default=None)
|
|
69
69
|
|
|
70
70
|
# Properties to return the private values
|
|
71
71
|
@property
|
|
@@ -94,35 +94,33 @@ Either a date-time or an interval, open or closed. Date and time expressions adh
|
|
|
94
94
|
raise ValueError(
|
|
95
95
|
"Maximum elevation must greater than minimum elevation"
|
|
96
96
|
)
|
|
97
|
-
|
|
98
|
-
if
|
|
99
|
-
raise ValueError(
|
|
100
|
-
"Maximum longitude must be greater than minimum longitude"
|
|
101
|
-
)
|
|
97
|
+
# Validate against WGS84
|
|
98
|
+
if xmin < -180 or ymin < -90 or xmax > 180 or ymax > 90:
|
|
99
|
+
raise ValueError("Bounding box must be within (-180, -90, 180, 90)")
|
|
102
100
|
|
|
103
101
|
if ymax < ymin:
|
|
104
102
|
raise ValueError(
|
|
105
103
|
"Maximum longitude must be greater than minimum longitude"
|
|
106
104
|
)
|
|
107
105
|
|
|
108
|
-
# Validate against WGS84
|
|
109
|
-
if xmin < -180 or ymin < -90 or xmax > 180 or ymax > 90:
|
|
110
|
-
raise ValueError("Bounding box must be within (-180, -90, 180, 90)")
|
|
111
|
-
|
|
112
106
|
return v
|
|
113
107
|
|
|
114
|
-
@field_validator("datetime")
|
|
108
|
+
@field_validator("datetime", mode="after")
|
|
115
109
|
@classmethod
|
|
116
|
-
def validate_datetime(
|
|
110
|
+
def validate_datetime(
|
|
111
|
+
cls, value: Optional[str], info: ValidationInfo
|
|
112
|
+
) -> Optional[str]:
|
|
117
113
|
"""validate datetime."""
|
|
118
114
|
# Split on "/" and replace no value or ".." with None
|
|
115
|
+
if value is None:
|
|
116
|
+
return value
|
|
119
117
|
values = [v if v and v != ".." else None for v in value.split("/")]
|
|
120
118
|
|
|
121
119
|
# If there are more than 2 dates, it's invalid
|
|
122
120
|
if len(values) > 2:
|
|
123
121
|
raise ValueError(
|
|
124
|
-
"""Invalid datetime range. Too many values.
|
|
125
|
-
Must match format: {begin_date}/{end_date}"""
|
|
122
|
+
"""Invalid datetime range. Too many values. """
|
|
123
|
+
"""Must match format: {begin_date}/{end_date}"""
|
|
126
124
|
)
|
|
127
125
|
|
|
128
126
|
# If there is only one date, duplicate to use for both start and end dates
|
|
@@ -149,8 +147,8 @@ Either a date-time or an interval, open or closed. Date and time expressions adh
|
|
|
149
147
|
)
|
|
150
148
|
|
|
151
149
|
# Store the parsed dates
|
|
152
|
-
|
|
153
|
-
|
|
150
|
+
info.data["_start_date"] = dates[0]
|
|
151
|
+
info.data["_end_date"] = dates[1]
|
|
154
152
|
|
|
155
153
|
# Return the original string value
|
|
156
154
|
return value
|
{stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/tests/test_collection_search.py
RENAMED
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import json
|
|
2
|
+
from datetime import datetime, timezone
|
|
2
3
|
from urllib.parse import quote_plus
|
|
3
4
|
|
|
4
5
|
import attr
|
|
@@ -88,6 +89,19 @@ class DummyPostClient(BaseCollectionSearchClient):
|
|
|
88
89
|
return search_request.model_dump()
|
|
89
90
|
|
|
90
91
|
|
|
92
|
+
def test_datetime_clean():
|
|
93
|
+
# ref: https://github.com/stac-utils/stac-pydantic/issues/170
|
|
94
|
+
utcnow = datetime.now(timezone.utc)
|
|
95
|
+
utcnow_str = utcnow.isoformat()
|
|
96
|
+
search = BaseCollectionSearchPostRequest(datetime=utcnow_str)
|
|
97
|
+
assert search.start_date == utcnow
|
|
98
|
+
assert search.end_date == utcnow
|
|
99
|
+
|
|
100
|
+
search = BaseCollectionSearchPostRequest()
|
|
101
|
+
assert not search.start_date
|
|
102
|
+
assert not search.end_date
|
|
103
|
+
|
|
104
|
+
|
|
91
105
|
def test_collection_search_extension_default():
|
|
92
106
|
"""Test GET - /collections endpoint with collection-search ext."""
|
|
93
107
|
api = StacApi(
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{stac_fastapi_extensions-5.0.2 → stac_fastapi_extensions-5.0.3}/stac_fastapi/extensions/__init__.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|