From 287509c1d795548280e419e946d96b76a73050a1 Mon Sep 17 00:00:00 2001 From: vincentsarago Date: Tue, 6 Feb 2024 22:49:06 +0100 Subject: [PATCH] remove collection path parameter and use concept_id query-parameter --- docs/src/API.md | 14 +++++++------- titiler/cmr/backend.py | 8 +++----- titiler/cmr/dependencies.py | 11 +++++++++-- titiler/cmr/factory.py | 20 ++++++-------------- 4 files changed, 25 insertions(+), 28 deletions(-) diff --git a/docs/src/API.md b/docs/src/API.md index 62ce405..9d38d10 100644 --- a/docs/src/API.md +++ b/docs/src/API.md @@ -4,20 +4,19 @@ ## Endpoint Description -`GET /collections/{collectionId}/tiles/{tileMatrixSetId}/{z}/{x}/{y}@{scale}x` +`GET /tiles/{tileMatrixSetId}/{z}/{x}/{y}@{scale}x` -`GET /collections/{collectionId}/tiles/{tileMatrixSetId}/{z}/{x}/{y}@{scale}x.{format}` +`GET /tiles/{tileMatrixSetId}/{z}/{x}/{y}@{scale}x.{format}` -`GET /collections/{collectionId}/tiles/{tileMatrixSetId}/{z}/{x}/{y}.{format}` +`GET /tiles/{tileMatrixSetId}/{z}/{x}/{y}.{format}` -`GET /collections/{collectionId}/tiles/{tileMatrixSetId}/{z}/{x}/{y}` +`GET /tiles/{tileMatrixSetId}/{z}/{x}/{y}` This endpoint provides tiled data for specific geographical locations and times. Tiles are defined by their x, y, and z coordinates. ## Parameters - **Path Parameters:** - - `collectionId` (string): The [concept ID](https://cmr.earthdata.nasa.gov/search/site/docs/search/api.html#c-concept-id) of the collection. - `tileMatrixSetId` (string): TileMatrixSet name (e.g **WebMercatorQuad**) - `x` (integer): The x coordinate of the tile - `y` (integer): The y coordinate of the tile @@ -26,8 +25,9 @@ This endpoint provides tiled data for specific geographical locations and times. - `format` (string, optional): Output image format, default is set to None and will be either JPEG or PNG depending on the presence of masked value. - **Query Parameters:** + - `concept_id` (string): The [concept ID](https://cmr.earthdata.nasa.gov/search/site/docs/search/api.html#c-concept-id) of the collection. **REQUIRED** - `temporal` (string, optional): Either a date-time or an interval. Date and time expressions adhere to 'YYYY-MM-DD' format. Intervals may be bounded or half-bounded (double-dots at start or end) **RECOMMENDED** - - `backend` (*cog* or *xarray*, optional): Backend to use in order to read the CMR dataset. Defaults to `cog` + - `backend` (*rasterio* or *xarray*, optional): Backend to use in order to read the CMR dataset. Defaults to `rasterio` - `variable`* (string, optional): The variable of interest. `required` when using `xarray` backend - `time_slice`* (string, optional): The time for which data is requested, in ISO 8601 format - `decode_times`* (bool, optional): Whether to decode times @@ -51,7 +51,7 @@ This endpoint provides tiled data for specific geographical locations and times. ## Request Example -GET /collections/C0000000000-YOCLOUD/tiles/WebMercatorQuad/1/2/3?backend=xarray&variable=temperature×tamp=2024-01-16T00:00:00Z&colormap=viridis&rescale=0,100&temporal=2024-01-16/2024-01-16 +GET /tiles/WebMercatorQuad/1/2/3?backend=xarray&variable=temperature×tamp=2024-01-16T00:00:00Z&colormap=viridis&rescale=0,100&temporal=2024-01-16/2024-01-16&concept_id=C0000000000-YOCLOUD ## Responses diff --git a/titiler/cmr/backend.py b/titiler/cmr/backend.py index 23af587..00d237f 100644 --- a/titiler/cmr/backend.py +++ b/titiler/cmr/backend.py @@ -49,9 +49,6 @@ class Asset(TypedDict, total=False): class CMRBackend(BaseBackend): """CMR Mosaic Backend.""" - # ConceptID - input: str = attr.ib() - tms: TileMatrixSet = attr.ib(default=WEB_MERCATOR_TMS) minzoom: int = attr.ib() maxzoom: int = attr.ib() @@ -70,6 +67,8 @@ class CMRBackend(BaseBackend): auth: Optional[Auth] = attr.ib(default=None) + input: str = attr.ib("CMR", init=False) + _backend_name = "CMR" def __attrs_post_init__(self) -> None: @@ -146,7 +145,7 @@ def assets_for_bbox( @cached( # type: ignore TTLCache(maxsize=cache_config.maxsize, ttl=cache_config.ttl), key=lambda self, xmin, ymin, xmax, ymax, **kwargs: hashkey( - self.input, xmin, ymin, xmax, ymax, **kwargs + xmin, ymin, xmax, ymax, **kwargs ), ) @retry( @@ -165,7 +164,6 @@ def get_assets( ) -> List[Asset]: """Find assets.""" results = earthaccess.search_data( - concept_id=self.input, bounding_box=(xmin, ymin, xmax, ymax), count=limit, **kwargs, diff --git a/titiler/cmr/dependencies.py b/titiler/cmr/dependencies.py index 591becc..9024b18 100644 --- a/titiler/cmr/dependencies.py +++ b/titiler/cmr/dependencies.py @@ -1,7 +1,7 @@ """titiler-cmr dependencies.""" from datetime import datetime -from typing import Dict, List, Literal, Optional, get_args +from typing import Any, Dict, List, Literal, Optional, get_args from fastapi import HTTPException, Query from starlette.requests import Request @@ -78,6 +78,12 @@ def OutputType( def cmr_query( + concept_id: Annotated[ + str, + Query( + description="A CMR concept id, in the format '-' " + ), + ], temporal: Annotated[ Optional[str], Query( @@ -92,7 +98,8 @@ def cmr_query( ] = None, ) -> Dict: """CMR Query options.""" - query = {} + query: Dict[str, Any] = {"concept_id": concept_id} + if temporal: dt = temporal.split("/") if len(dt) > 2: diff --git a/titiler/cmr/factory.py b/titiler/cmr/factory.py index e4c767d..341db62 100644 --- a/titiler/cmr/factory.py +++ b/titiler/cmr/factory.py @@ -370,33 +370,27 @@ def register_tiles(self): # noqa: C901 """Register tileset endpoints.""" @self.router.get( - "/collections/{collectionId}/tiles/{tileMatrixSetId}/{z}/{x}/{y}", + "/tiles/{tileMatrixSetId}/{z}/{x}/{y}", **img_endpoint_params, tags=["Raster Tiles"], ) @self.router.get( - "/collections/{collectionId}/tiles/{tileMatrixSetId}/{z}/{x}/{y}.{format}", + "/tiles/{tileMatrixSetId}/{z}/{x}/{y}.{format}", **img_endpoint_params, tags=["Raster Tiles"], ) @self.router.get( - "/collections/{collectionId}/tiles/{tileMatrixSetId}/{z}/{x}/{y}@{scale}x", + "/tiles/{tileMatrixSetId}/{z}/{x}/{y}@{scale}x", **img_endpoint_params, tags=["Raster Tiles"], ) @self.router.get( - "/collections/{collectionId}/tiles/{tileMatrixSetId}/{z}/{x}/{y}@{scale}x.{format}", + "/tiles/{tileMatrixSetId}/{z}/{x}/{y}@{scale}x.{format}", **img_endpoint_params, tags=["Raster Tiles"], ) def tiles_endpoint( request: Request, - collectionId: Annotated[ - str, - Path( - description="A CMR concept id, in the format '-' " - ), - ], tileMatrixSetId: Annotated[ Literal[tuple(self.supported_tms.list())], Path(description="Identifier for a supported TileMatrixSet"), @@ -431,9 +425,9 @@ def tiles_endpoint( query=Depends(cmr_query), ################################################################### backend: Annotated[ - Literal["cog", "xarray"], + Literal["rasterio", "xarray"], Query(description="Backend to read the CMR dataset"), - ] = "cog", + ] = "rasterio", ################################################################### # ZarrReader Options ################################################################### @@ -548,7 +542,6 @@ def tiles_endpoint( reader_options = {} with CMRBackend( - collectionId, tms=tms, reader=reader, reader_options=reader_options, @@ -741,7 +734,6 @@ def tilejson_endpoint( # type: ignore # TODO: can we get metadata from the collection? with CMRBackend( - collectionId, auth=request.app.state.cmr_auth, tms=tms, ) as src_dst: