"""rio-tiler dynamic tile server for Natural Earth HYP_HR_SR_OB_DR (global basemap)""" import os from pathlib import Path from fastapi import FastAPI, HTTPException from fastapi.responses import HTMLResponse from starlette.requests import Request from starlette.responses import Response from rio_tiler.errors import TileOutsideBounds from rio_tiler.io import Reader from rio_tiler.profiles import img_profiles DATA_PATH = str(Path(__file__).parent / "data" / "HYP_HR_SR_OB_DR_cog.tif") app = FastAPI( title="rio-tiler world", description="Global basemap tile server - Natural Earth HYP_HR_SR_OB_DR", ) @app.get( "/tiles/{z}/{x}/{y}.png", responses={ 200: {"content": {"image/png": {}}, "description": "Return a PNG tile."}, 404: {"description": "Tile outside bounds."}, }, response_class=Response, description="Read global COG tile and return PNG (uint8 RGB, no rescaling needed)", ) def tile(z: int, x: int, y: int): """Return a map tile for the given z/x/y coordinates.""" try: with Reader(DATA_PATH) as cog: img = cog.tile(x, y, z) except TileOutsideBounds: raise HTTPException(status_code=404, detail="Tile outside bounds") content = img.render( img_format="PNG", **img_profiles.get("png", {}), ) return Response(content, media_type="image/png") @app.get("/tilejson.json", responses={200: {"description": "Return a TileJSON document"}}) def tilejson(request: Request): """Return a TileJSON 2.2.0 document.""" with Reader(DATA_PATH) as cog: bounds = cog.get_geographic_bounds(cog.tms.rasterio_geographic_crs) minzoom = cog.minzoom maxzoom = cog.maxzoom base_url = str(request.base_url).rstrip("/") tile_url = f"{base_url}/tiles/{{z}}/{{x}}/{{y}}.png" return { "tilejson": "2.2.0", "name": "Natural Earth - HYP_HR_SR_OB_DR", "description": "Natural Earth cross-blended hypsometric tints with shaded relief", "tiles": [tile_url], "bounds": list(bounds), "minzoom": minzoom, "maxzoom": maxzoom, "center": [0, 20, minzoom], }