{"id":1768,"date":"2026-11-06T06:58:28","date_gmt":"2026-11-06T06:58:28","guid":{"rendered":"https:\/\/helpwithmygisassignment.com\/blog\/?p=1768"},"modified":"2026-11-06T06:58:49","modified_gmt":"2026-11-06T06:58:49","slug":"serverless-cog-dynamic-mosaicing-titiler-aws-lambda","status":"publish","type":"post","link":"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/","title":{"rendered":"Building a Serverless Cloud-Optimized GeoTIFF (COG) Dynamic Mosaicing Pipeline with AWS Lambda and TiTiler"},"content":{"rendered":"<div id=\"ez-toc-container\" class=\"ez-toc-v2_0_89 counter-hierarchy ez-toc-counter ez-toc-grey ez-toc-container-direction\">\n<div class=\"ez-toc-title-container\">\n<p class=\"ez-toc-title\" style=\"cursor:inherit\">Table of Contents<\/p>\n<span class=\"ez-toc-title-toggle\"><a href=\"#\" class=\"ez-toc-pull-right ez-toc-btn ez-toc-btn-xs ez-toc-btn-default ez-toc-toggle\" aria-label=\"Toggle Table of Content\"><span class=\"ez-toc-js-icon-con\"><span class=\"\"><span class=\"eztoc-hide\" style=\"display:none;\">Toggle<\/span><span class=\"ez-toc-icon-toggle-span\"><svg style=\"fill: #999;color:#999\" xmlns=\"http:\/\/www.w3.org\/2000\/svg\" class=\"list-377408\" width=\"20px\" height=\"20px\" viewBox=\"0 0 24 24\" fill=\"none\"><path d=\"M6 6H4v2h2V6zm14 0H8v2h12V6zM4 11h2v2H4v-2zm16 0H8v2h12v-2zM4 16h2v2H4v-2zm16 0H8v2h12v-2z\" fill=\"currentColor\"><\/path><\/svg><svg style=\"fill: #999;color:#999\" class=\"arrow-unsorted-368013\" xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"10px\" height=\"10px\" viewBox=\"0 0 24 24\" version=\"1.2\" baseProfile=\"tiny\"><path d=\"M18.2 9.3l-6.2-6.3-6.2 6.3c-.2.2-.3.4-.3.7s.1.5.3.7c.2.2.4.3.7.3h11c.3 0 .5-.1.7-.3.2-.2.3-.5.3-.7s-.1-.5-.3-.7zM5.8 14.7l6.2 6.3 6.2-6.3c.2-.2.3-.5.3-.7s-.1-.5-.3-.7c-.2-.2-.4-.3-.7-.3h-11c-.3 0-.5.1-.7.3-.2.2-.3.5-.3.7s.1.5.3.7z\"\/><\/svg><\/span><\/span><\/span><\/a><\/span><\/div>\n<nav><ul class='ez-toc-list ez-toc-list-level-1 ' ><li class='ez-toc-page-1 ez-toc-heading-level-1'><a class=\"ez-toc-link ez-toc-heading-1\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#Building_a_Serverless_Cloud-Optimized_GeoTIFF_COG_Dynamic_Mosaicing_Pipeline_with_AWS_Lambda_and_TiTiler\" >Building a Serverless Cloud-Optimized GeoTIFF (COG) Dynamic Mosaicing Pipeline with AWS Lambda and TiTiler<\/a><ul class='ez-toc-list-level-2' ><li class='ez-toc-heading-level-2'><a class=\"ez-toc-link ez-toc-heading-2\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#Introduction\" >Introduction<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-2'><a class=\"ez-toc-link ez-toc-heading-3\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#1_System_Architecture\" >1. System Architecture<\/a><ul class='ez-toc-list-level-3' ><li class='ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-4\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#11_Amazon_S3_COG_storage\" >1.1 Amazon S3: COG storage<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-5\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#12_MosaicJSON_spatial_indexing_and_asset_selection\" >1.2 MosaicJSON: spatial indexing and asset selection<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-6\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#13_TiTiler_and_AWS_Lambda_dynamic_rendering\" >1.3 TiTiler and AWS Lambda: dynamic rendering<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-7\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#14_API_Gateway_CloudFront_and_the_client\" >1.4 API Gateway, CloudFront, and the client<\/a><\/li><\/ul><\/li><li class='ez-toc-page-1 ez-toc-heading-level-2'><a class=\"ez-toc-link ez-toc-heading-8\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#2_Step_One_Structure_Satellite_Scenes_and_Generate_a_MosaicJSON_Catalog\" >2. Step One: Structure Satellite Scenes and Generate a MosaicJSON Catalog<\/a><ul class='ez-toc-list-level-3' ><li class='ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-9\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#21_Validate_source_COGs\" >2.1 Validate source COGs<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-10\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#22_Maintain_a_manifest_of_eligible_assets\" >2.2 Maintain a manifest of eligible assets<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-11\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#23_Generate_the_MosaicJSON_catalog\" >2.3 Generate the MosaicJSON catalog<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-12\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#24_Design_catalog_boundaries_deliberately\" >2.4 Design catalog boundaries deliberately<\/a><\/li><\/ul><\/li><li class='ez-toc-page-1 ez-toc-heading-level-2'><a class=\"ez-toc-link ez-toc-heading-13\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#3_Step_Two_Package_TiTiler_as_an_AWS_Lambda_Container\" >3. Step Two: Package TiTiler as an AWS Lambda Container<\/a><ul class='ez-toc-list-level-3' ><li class='ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-14\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#31_Choose_the_correct_TiTiler_package\" >3.1 Choose the correct TiTiler package<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-15\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#32_Create_the_Lambda_handler\" >3.2 Create the Lambda handler<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-16\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#33_Build_the_Docker_image\" >3.3 Build the Docker image<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-17\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#34_Push_the_image_to_Amazon_ECR\" >3.4 Push the image to Amazon ECR<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-18\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#35_Configure_Lambda_execution_settings\" >3.5 Configure Lambda execution settings<\/a><\/li><\/ul><\/li><li class='ez-toc-page-1 ez-toc-heading-level-2'><a class=\"ez-toc-link ez-toc-heading-19\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#4_Step_Three_Expose_Tile_Endpoints_Through_API_Gateway\" >4. Step Three: Expose Tile Endpoints Through API Gateway<\/a><ul class='ez-toc-list-level-3' ><li class='ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-20\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#Test_the_API_before_connecting_a_map\" >Test the API before connecting a map<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-21\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#Connect_MapLibre_or_Leaflet\" >Connect MapLibre or Leaflet<\/a><\/li><\/ul><\/li><li class='ez-toc-page-1 ez-toc-heading-level-2'><a class=\"ez-toc-link ez-toc-heading-22\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#5_Step_Four_Add_CloudFront_Caching_and_Optimize_Request_Costs\" >5. Step Four: Add CloudFront Caching and Optimize Request Costs<\/a><ul class='ez-toc-list-level-3' ><li class='ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-23\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#51_Cache_the_final_rendered_tile\" >5.1 Cache the final rendered tile<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-24\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#52_Build_a_cache_key_that_matches_rendering_behavior\" >5.2 Build a cache key that matches rendering behavior<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-25\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#53_Version_the_catalog_instead_of_overwriting_it\" >5.3 Version the catalog instead of overwriting it<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-26\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#54_Measure_where_costs_originate\" >5.4 Measure where costs originate<\/a><\/li><\/ul><\/li><li class='ez-toc-page-1 ez-toc-heading-level-2'><a class=\"ez-toc-link ez-toc-heading-27\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#6_Production_Engineering_Security_Performance_and_Reliability\" >6. Production Engineering: Security, Performance, and Reliability<\/a><ul class='ez-toc-list-level-3' ><li class='ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-28\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#61_Restrict_data_access\" >6.1 Restrict data access<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-29\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#62_Tune_for_raster_workloads\" >6.2 Tune for raster workloads<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-30\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#63_Make_mosaicking_semantics_explicit\" >6.3 Make mosaicking semantics explicit<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-31\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#64_Plan_for_failure_and_observability\" >6.4 Plan for failure and observability<\/a><\/li><\/ul><\/li><li class='ez-toc-page-1 ez-toc-heading-level-2'><a class=\"ez-toc-link ez-toc-heading-32\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#7_SEO_Interlinking_and_Related_Architecture_Guides\" >7. SEO Interlinking and Related Architecture Guides<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-2'><a class=\"ez-toc-link ez-toc-heading-33\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/#Summary_and_Enterprise_Takeaways\" >Summary and Enterprise Takeaways<\/a><\/li><\/ul><\/li><\/ul><\/nav><\/div>\n<h1><span class=\"ez-toc-section\" id=\"Building_a_Serverless_Cloud-Optimized_GeoTIFF_COG_Dynamic_Mosaicing_Pipeline_with_AWS_Lambda_and_TiTiler\"><\/span>Building a Serverless Cloud-Optimized GeoTIFF (COG) Dynamic Mosaicing Pipeline with AWS Lambda and TiTiler<code><\/code><span class=\"ez-toc-section-end\"><\/span><\/h1>\n<h2><span class=\"ez-toc-section\" id=\"Introduction\"><\/span>Introduction<span class=\"ez-toc-section-end\"><\/span><\/h2>\n<p>Pre-rendering an XYZ tile pyramid has traditionally been a practical way to publish satellite imagery to web mapping applications. However, maintaining static tile pyramids becomes increasingly expensive when a platform manages millions of raster scenes, multiple acquisition dates, overlapping satellite footprints, and frequently updated imagery collections.<\/p>\n<p>Every change to a source image or rendering configuration can require additional tile generation, storage, and cache invalidation. Worse, users cannot easily request a new combination of scenes, spectral bands, or processing parameters without introducing another preprocessing workflow.<\/p>\n<p>A <strong>Serverless COG Dynamic Mosaicing TiTiler AWS Lambda<\/strong> architecture addresses these challenges by separating raster storage, spatial indexing, and tile rendering.<\/p>\n<p><a href=\"https:\/\/helpwithmygisassignment.com\/blog\/cloud-optimized-geotiff-web-map-architecture\/\">Cloud-Optimized GeoTIFFs (COGs)<\/a> retain imagery in a tiled, overview-enabled raster format designed for efficient access through HTTP range requests. Rather than downloading an entire scene, a compatible reader retrieves the image regions and metadata required for a particular operation. The <a href=\"https:\/\/www.ogc.org\/standards\/ogc-cloud-optimized-geotiff\/\" target=\"_blank\" rel=\"noopener\">OGC Cloud Optimized GeoTIFF standard<\/a> formalizes the key requirements behind this approach.<\/p>\n<p>TiTiler builds on these capabilities to generate raster tiles dynamically. AWS Lambda executes the rendering application on demand, Amazon S3 stores the source imagery, and MosaicJSON provides spatial indexing for collections of overlapping COGs. API Gateway exposes the service to clients, while CloudFront caches frequently requested output tiles.<\/p>\n<p>The result is a cloud-native raster delivery pipeline that can support changing satellite collections without requiring a complete static tile pyramid.<\/p>\n<p>This guide develops the architecture, implementation workflow, deployment configuration, caching strategy, and production engineering considerations.<\/p>\n<h2><span class=\"ez-toc-section\" id=\"1_System_Architecture\"><\/span>1. System Architecture<span class=\"ez-toc-section-end\"><\/span><\/h2>\n<p>The proposed architecture separates the data plane from the rendering and delivery layers.<\/p>\n<p><strong>Image 1: Architecture diagram of a serverless COG tile rendering pipeline with AWS Lambda and S3<\/strong><\/p>\n<p><strong>Alt Text:<\/strong> System architecture diagram illustrating serverless Cloud-Optimized GeoTIFF dynamic tile rendering using AWS Lambda, TiTiler, and Amazon S3.<\/p>\n<p>Suggested diagram flow:<\/p>\n<pre><code>Satellite ingestion \/ STAC catalog\r\n              |\r\n              v\r\n      COG validation and QA\r\n              |\r\n              v\r\n       Amazon S3 imagery\r\n              |\r\n              v\r\n    MosaicJSON catalog builder\r\n              |\r\n              v\r\n Amazon S3 metadata catalog\r\n              |\r\n              v\r\n MapLibre \/ Leaflet client\r\n              |\r\n              v\r\n          CloudFront\r\n              |\r\n              v\r\n        API Gateway\r\n              |\r\n              v\r\n     AWS Lambda + TiTiler\r\n              |\r\n              +------&gt; Read selected COG byte ranges\r\n              |                  |\r\n              |                  v\r\n              |             Amazon S3\r\n              |\r\n              v\r\n       Rendered raster tile\r\n              |\r\n              v\r\n        CloudFront cache<\/code><\/pre>\n<p>The catalog builder can run as a separate batch or event-driven workload. It should not rebuild a large mosaic during every web request.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"11_Amazon_S3_COG_storage\"><\/span>1.1 Amazon S3: COG storage<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>S3 stores the original raster assets and versioned MosaicJSON catalogs. Organize imagery by collection, acquisition date, and scene identifier so that individual assets can be managed independently.<\/p>\n<p>For example:<\/p>\n<pre><code>s3:\/\/geo-data-prod\/\r\n\u251c\u2500\u2500 sentinel2\/\r\n\u2502   \u251c\u2500\u2500 2026\/10\/scene_001.tif\r\n\u2502   \u2514\u2500\u2500 2026\/10\/scene_002.tif\r\n\u2514\u2500\u2500 catalogs\/\r\n    \u2514\u2500\u2500 sentinel2\/\r\n        \u251c\u2500\u2500 v2026-10-28\/\r\n        \u2502   \u2514\u2500\u2500 mosaic.json\r\n        \u2514\u2500\u2500 v2026-10-28\/\r\n            \u2514\u2500\u2500 catalog-metadata.json<\/code><\/pre>\n<p>Use immutable versioned catalog paths in production. This prevents a catalog update from silently changing the imagery behind previously cached tiles.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"12_MosaicJSON_spatial_indexing_and_asset_selection\"><\/span>1.2 MosaicJSON: spatial indexing and asset selection<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>MosaicJSON describes the relationship between raster assets and the spatial regions they cover. It allows a mosaic-aware reader to identify candidate images for a requested tile instead of opening every scene in the archive.<\/p>\n<p>The open-source <code><a href=\"https:\/\/developmentseed.org\/cogeo-mosaic\/\" target=\"_blank\" rel=\"noopener\">cogeo-mosaic<\/a><\/code> project generates and manages MosaicJSON definitions.<\/p>\n<p>A MosaicJSON catalog is metadata, not a new merged raster. The source COGs remain separate objects in S3.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"13_TiTiler_and_AWS_Lambda_dynamic_rendering\"><\/span>1.3 TiTiler and AWS Lambda: dynamic rendering<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>TiTiler is a FastAPI-based dynamic raster tiling service with support for COG, STAC, and MosaicJSON workflows. Its default application exposes raster tile endpoints and related metadata operations. See the <a href=\"https:\/\/developmentseed.org\/titiler\/\" target=\"_blank\" rel=\"noopener\">official TiTiler documentation<\/a>.<\/p>\n<p>Lambda runs the application without requiring a permanently running tile-server fleet. When a request arrives, the service identifies the relevant COG assets, retrieves the required raster data, applies the requested rendering configuration, and returns an image.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"14_API_Gateway_CloudFront_and_the_client\"><\/span>1.4 API Gateway, CloudFront, and the client<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>API Gateway provides an HTTP interface to the rendering function. CloudFront sits in front of that interface to cache repeat requests close to users.<\/p>\n<p>MapLibre GL JS and Leaflet consume the resulting PNG or JPEG tiles through standard raster-layer interfaces.<\/p>\n<p>This arrangement is particularly useful for interactive environmental dashboards, land-cover monitoring, disaster response, agricultural intelligence, and satellite imagery portals.<\/p>\n<h2><span class=\"ez-toc-section\" id=\"2_Step_One_Structure_Satellite_Scenes_and_Generate_a_MosaicJSON_Catalog\"><\/span>2. Step One: Structure Satellite Scenes and Generate a MosaicJSON Catalog<span class=\"ez-toc-section-end\"><\/span><\/h2>\n<p>The quality of a dynamic tile server depends on the quality of its input data and spatial index. Building MosaicJSON should therefore be part of the imagery ingestion pipeline, not an incidental deployment task.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"21_Validate_source_COGs\"><\/span>2.1 Validate source COGs<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>Before adding a scene to the archive, confirm that the file is a valid COG and that its spatial metadata is correct.<\/p>\n<p>Typical preprocessing checks include:<\/p>\n<ul>\n<li>Valid CRS, geotransform, dimensions, and bounds.<\/li>\n<li>Internal tiling and suitable overview levels.<\/li>\n<li>Correct NoData values, band descriptions, and data types.<\/li>\n<li>Consistent band order and scale\/offset interpretation across the intended collection.<\/li>\n<li>Working remote range access and appropriate S3 permissions.<\/li>\n<\/ul>\n<p>Use GDAL&#8217;s COG driver when converting source rasters. For example:<\/p>\n<pre><code>gdal_translate \\\r\n  source.tif \\\r\n  scene_001.tif \\\r\n  -of COG \\\r\n  -co COMPRESS=DEFLATE \\\r\n  -co BLOCKSIZE=512<\/code><\/pre>\n<p>The correct compression and overview resampling method depends on the raster data. Continuous imagery may benefit from averaging, while categorical land-cover rasters generally require nearest-neighbor or another suitable categorical method.<\/p>\n<p>For reproducible processing, pin the GDAL version and record the conversion options in the ingestion metadata.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"22_Maintain_a_manifest_of_eligible_assets\"><\/span>2.2 Maintain a manifest of eligible assets<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>Maintain a manifest that records each scene&#8217;s identifier, S3 URI, acquisition time, collection, processing level, footprint, and quality-control status.<\/p>\n<p>For example, a text file accepted by <code>cogeo-mosaic<\/code> can contain one COG path per line:<\/p>\n<pre><code>s3:\/\/geo-data-prod\/sentinel2\/2026\/10\/scene_001.tif\r\ns3:\/\/geo-data-prod\/sentinel2\/2026\/10\/scene_002.tif\r\ns3:\/\/geo-data-prod\/sentinel2\/2026\/10\/scene_003.tif<\/code><\/pre>\n<p>Generate this manifest from the ingestion or STAC discovery workflow rather than repeatedly listing an entire archive during requests.<\/p>\n<p>A <a href=\"https:\/\/stacspec.org\/\" target=\"_blank\" rel=\"noopener\">STAC API satellite imagery pipeline<\/a> is a useful upstream integration: filter scenes by geography, time, collection, and quality attributes before generating the mosaic catalog.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"23_Generate_the_MosaicJSON_catalog\"><\/span>2.3 Generate the MosaicJSON catalog<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>Install the <code>cogeo-mosaic<\/code> package in a controlled build environment and create the mosaic definition:<\/p>\n<pre><code>python -m pip install cogeo-mosaic\r\n\r\ncogeo-mosaic create \\\r\n  scenes.txt \\\r\n  -o mosaic.json \\\r\n  --threads 8<\/code><\/pre>\n<p>The command accepts a list of valid COG inputs and writes a MosaicJSON definition. Review the <code><a href=\"https:\/\/developmentseed.org\/cogeo-mosaic\/cli\/\" target=\"_blank\" rel=\"noopener\">cogeo-mosaic<\/a><\/code><a href=\"https:\/\/developmentseed.org\/cogeo-mosaic\/cli\/\" target=\"_blank\" rel=\"noopener\"> CLI documentation<\/a> for supported options, including zoom controls and tile-coverage sorting.<\/p>\n<p>Validate the generated catalog and test that its asset references resolve correctly from the environment that will run TiTiler. The catalog builder&#8217;s AWS identity and the runtime Lambda identity may be different, so test both permissions separately.<\/p>\n<p>Upload the generated catalog to a versioned S3 location:<\/p>\n<pre><code>aws s3 cp mosaic.json \\\r\n  s3:\/\/geo-data-prod\/catalogs\/sentinel2\/v2026-10-28\/mosaic.json<\/code><\/pre>\n<p>Keep a small deployment manifest alongside the catalog containing the build timestamp, source collection, selected scenes, software versions, and a checksum.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"24_Design_catalog_boundaries_deliberately\"><\/span>2.4 Design catalog boundaries deliberately<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>A single catalog containing every scene in a long-running satellite archive may become difficult to maintain. Generate separate catalogs for meaningful dimensions such as product type, region, acquisition period, or processing level.<\/p>\n<p>For example:<\/p>\n<pre><code>\/catalogs\/sentinel2\/region-a\/2026-10\/mosaic.json\r\n\/catalogs\/sentinel2\/region-b\/2026-10\/mosaic.json\r\n\/catalogs\/landsat\/region-a\/2026-10\/mosaic.json<\/code><\/pre>\n<p>This gives the service smaller metadata scopes and allows new versions to be published independently.<\/p>\n<p>One important distinction: a spatial mosaic index is not inherently a temporal query engine. If users need the newest cloud-free scene, latest acquisition, or a particular time interval, implement that selection in the upstream catalog-generation workflow or a controlled STAC-aware service. Do not assume that simply putting every scene into MosaicJSON automatically produces the desired temporal composite.<\/p>\n<h2><span class=\"ez-toc-section\" id=\"3_Step_Two_Package_TiTiler_as_an_AWS_Lambda_Container\"><\/span>3. Step Two: Package TiTiler as an AWS Lambda Container<span class=\"ez-toc-section-end\"><\/span><\/h2>\n<p>Raster libraries can include substantial native dependencies. A container image provides a reproducible deployment unit containing the Python runtime, TiTiler, Rasterio\/GDAL dependencies, and Lambda handler.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"31_Choose_the_correct_TiTiler_package\"><\/span>3.1 Choose the correct TiTiler package<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>For the full default application, use <code>titiler.application<\/code>. Current TiTiler packaging is divided into separate namespace packages; avoid relying on the old <code>titiler<\/code> metapackage.<\/p>\n<p>For applications that only need a small subset of endpoints, a custom FastAPI application built from <code>titiler.core<\/code> and <code>titiler.mosaic<\/code> can reduce unnecessary dependencies. The trade-off is that custom endpoint registration and configuration must be maintained and tested by the team.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"32_Create_the_Lambda_handler\"><\/span>3.2 Create the Lambda handler<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>TiTiler&#8217;s FastAPI application uses ASGI, while Lambda invokes functions through an event-and-context interface. Mangum bridges this difference.<\/p>\n<p>Create <code>app.py<\/code>:<\/p>\n<pre><code>from mangum import Mangum\r\nfrom titiler.application.main import app\r\n\r\nhandler = Mangum(app, enable_lifespan=False)<\/code><\/pre>\n<p>This uses TiTiler&#8217;s default application and routes. Verify that the chosen TiTiler and Mangum versions are compatible with the handler configuration before pinning them for a production release.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"33_Build_the_Docker_image\"><\/span>3.3 Build the Docker image<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>Create <code>requirements.txt<\/code>:<\/p>\n<pre><code>titiler.application\r\nmangum<\/code><\/pre>\n<p>These entries illustrate the package selection. For a production build, lock exact versions and resolve dependencies in CI so that rebuilding the image does not silently change native libraries or API behavior.<\/p>\n<p>Create a <code>Dockerfile<\/code>:<\/p>\n<pre><code>FROM public.ecr.aws\/lambda\/python:3.12\r\n\r\nENV GDAL_DISABLE_READDIR_ON_OPEN=EMPTY_DIR\r\n\r\nCOPY requirements.txt ${LAMBDA_TASK_ROOT}\/requirements.txt\r\n\r\nRUN pip install --no-cache-dir \\\r\n    -r ${LAMBDA_TASK_ROOT}\/requirements.txt\r\n\r\nCOPY app.py ${LAMBDA_TASK_ROOT}\/app.py\r\n\r\nCMD [\"app.handler\"]<\/code><\/pre>\n<p>This is a simple baseline rather than a guarantee of a minimal image. The full application includes more dependencies than a purpose-built mosaic-only service. Measure the resulting image size, cold-start behavior, and import time before selecting the final build.<\/p>\n<p>AWS supports Lambda container images up to 10 GB uncompressed. Use a compatible single target architecture and build the image accordingly. Consult <a href=\"https:\/\/docs.aws.amazon.com\/lambda\/latest\/dg\/images-create.html\" target=\"_blank\" rel=\"noopener\">AWS&#8217;s Lambda container image requirements<\/a>.<\/p>\n<p>For an x86-64 Lambda deployment, build and test locally:<\/p>\n<pre><code>docker build \\\r\n  --platform linux\/amd64 \\\r\n  --provenance=false \\\r\n  -t titiler-mosaic:latest .\r\n\r\ndocker run --rm -p 9000:8080 titiler-mosaic:latest<\/code><\/pre>\n<p>The AWS Lambda base image includes the runtime interface components required by Lambda. For local testing, invoke its runtime emulator with a Lambda event using the appropriate runtime path.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"34_Push_the_image_to_Amazon_ECR\"><\/span>3.4 Push the image to Amazon ECR<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>Create an ECR repository in the same AWS Region as the Lambda function:<\/p>\n<pre><code>export AWS_REGION=us-east-1\r\nexport ACCOUNT_ID=$(aws sts get-caller-identity \\\r\n  --query Account --output text)\r\n\r\naws ecr create-repository \\\r\n  --repository-name titiler-mosaic \\\r\n  --region \"$AWS_REGION\"\r\n\r\naws ecr get-login-password --region \"$AWS_REGION\" \\\r\n  | docker login \\\r\n      --username AWS \\\r\n      --password-stdin \\\r\n      \"$ACCOUNT_ID.dkr.ecr.$AWS_REGION.amazonaws.com\"\r\n\r\ndocker tag titiler-mosaic:latest \\\r\n  \"$ACCOUNT_ID.dkr.ecr.$AWS_REGION.amazonaws.com\/titiler-mosaic:v1\"\r\n\r\ndocker push \\\r\n  \"$ACCOUNT_ID.dkr.ecr.$AWS_REGION.amazonaws.com\/titiler-mosaic:v1\"<\/code><\/pre>\n<p>Use immutable image tags or image digests in release pipelines instead of depending on a mutable <code>latest<\/code> tag.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"35_Configure_Lambda_execution_settings\"><\/span>3.5 Configure Lambda execution settings<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>Create the function using the image in ECR. A representative starting configuration for a tile-rendering workload is:<\/p>\n<pre><code>aws lambda create-function \\\r\n  --function-name titiler-mosaic \\\r\n  --package-type Image \\\r\n  --code ImageUri=\"$ACCOUNT_ID.dkr.ecr.$AWS_REGION.amazonaws.com\/titiler-mosaic:v1\" \\\r\n  --role arn:aws:iam::&lt;ACCOUNT_ID&gt;:role\/TiTilerExecutionRole \\\r\n  --timeout 25 \\\r\n  --memory-size 2048 \\\r\n  --ephemeral-storage '{\"Size\":1024}' \\\r\n  --architectures x86_64 \\\r\n  --region \"$AWS_REGION\"<\/code><\/pre>\n<p>Replace the example role ARN with the actual execution role. The role should have CloudWatch Logs permissions and narrowly scoped <code>s3:GetObject<\/code> access to the intended raster and catalog prefixes. Add KMS permissions where customer-managed encryption keys require them.<\/p>\n<p>The memory and timeout values are starting points, not universal production settings. Increase memory if CPU-bound rendering is slow, and configure ephemeral storage only when local temporary files require it. Lambda supports up to 15 minutes per invocation, but the practical timeout for interactive tiles is usually much shorter and must also fit the API Gateway integration&#8217;s limits.<\/p>\n<p>For the official project-managed deployment approach, examine <a href=\"https:\/\/developmentseed.org\/titiler\/deployment\/aws\/lambda\/\" target=\"_blank\" rel=\"noopener\">TiTiler&#8217;s AWS Lambda deployment documentation<\/a>, which describes its CDK-based infrastructure.<\/p>\n<h2><span class=\"ez-toc-section\" id=\"4_Step_Three_Expose_Tile_Endpoints_Through_API_Gateway\"><\/span>4. Step Three: Expose Tile Endpoints Through API Gateway<span class=\"ez-toc-section-end\"><\/span><\/h2>\n<p><img loading=\"lazy\" decoding=\"async\" class=\"aligncenter size-large wp-image-1873\" src=\"https:\/\/helpwithmygisassignment.com\/blog\/wp-content\/uploads\/2026\/11\/Gemini_Generated_Image_f4sswbf4sswbf4ss-1024x572.jpg\" alt=\"Serverless COG Dynamic Mosaicing TiTiler AWS Lambda workflow diagram\" width=\"1024\" height=\"572\" srcset=\"https:\/\/helpwithmygisassignment.com\/blog\/wp-content\/uploads\/2026\/11\/Gemini_Generated_Image_f4sswbf4sswbf4ss-1024x572.jpg 1024w, https:\/\/helpwithmygisassignment.com\/blog\/wp-content\/uploads\/2026\/11\/Gemini_Generated_Image_f4sswbf4sswbf4ss-300x167.jpg 300w, https:\/\/helpwithmygisassignment.com\/blog\/wp-content\/uploads\/2026\/11\/Gemini_Generated_Image_f4sswbf4sswbf4ss-768x429.jpg 768w, https:\/\/helpwithmygisassignment.com\/blog\/wp-content\/uploads\/2026\/11\/Gemini_Generated_Image_f4sswbf4sswbf4ss.jpg 1376w\" sizes=\"auto, (max-width: 1024px) 100vw, 1024px\" \/><\/p>\n<p>After deploying the function, create an API Gateway HTTP API with a Lambda proxy integration. Use a catch-all route such as <code>$default<\/code> or suitable proxy routes so requests for metadata, TileJSON, and raster tiles reach the same application.<\/p>\n<p>Configure the integration and invoke permissions, then confirm that the API forwards the complete request path and query string to the Lambda handler.<\/p>\n<p>A MosaicJSON tile endpoint typically follows this pattern:<\/p>\n<pre><code>\/mosaicjson\/tiles\/WebMercatorQuad\/{z}\/{x}\/{y}.png?url={mosaic_json_url}<\/code><\/pre>\n<p>For example, an encoded catalog URL could look like:<\/p>\n<pre><code>https:\/\/tiles.example.com\/mosaicjson\/tiles\/WebMercatorQuad\/8\/74\/96.png?url=s3%3A%2F%2Fgeo-data-prod%2Fcatalogs%2Fsentinel2%2Fv2026-10-28%2Fmosaic.json<\/code><\/pre>\n<p>The <code>url<\/code> parameter identifies the MosaicJSON input. TiTiler&#8217;s <a href=\"https:\/\/developmentseed.org\/titiler\/endpoints\/mosaic\/\" target=\"_blank\" rel=\"noopener\">MosaicJSON endpoint reference<\/a> documents tile generation, TileJSON, metadata, and asset-inspection routes.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"Test_the_API_before_connecting_a_map\"><\/span>Test the API before connecting a map<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>Check the catalog&#8217;s metadata endpoint first, then request a small number of image tiles:<\/p>\n<pre><code>curl -i \\\r\n  \"https:\/\/tiles.example.com\/mosaicjson\/tiles\/WebMercatorQuad\/8\/74\/96.png?url=&lt;ENCODED_MOSAIC_URL&gt;\" \\\r\n  -o test-tile.png<\/code><\/pre>\n<p>Replace the placeholder with the correctly URL-encoded catalog URI. Inspect the response status, headers, and image. Successful responses should have the appropriate image content type, such as <code>image\/png<\/code>.<\/p>\n<p>API Gateway proxy behavior, binary responses, CORS configuration, and integration timeouts must be tested with the chosen API type. See the <a href=\"https:\/\/docs.aws.amazon.com\/apigateway\/latest\/developerguide\/lambda-proxy-binary-media.html\" target=\"_blank\" rel=\"noopener\">AWS API Gateway binary response guidance<\/a> when using a REST API that requires explicit binary media configuration.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"Connect_MapLibre_or_Leaflet\"><\/span>Connect MapLibre or Leaflet<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>Once the service returns valid raster tiles, a web mapping client can add the mosaic as a raster source.<\/p>\n<p>For MapLibre GL JS:<\/p>\n<pre><code>map.addSource(\"satellite-mosaic\", {\r\n  type: \"raster\",\r\n  tiles: [\r\n    \"https:\/\/tiles.example.com\/mosaicjson\/tiles\/WebMercatorQuad\/{z}\/{x}\/{y}.png?url=&lt;ENCODED_MOSAIC_URL&gt;\"\r\n  ],\r\n  tileSize: 256\r\n});\r\n\r\nmap.addLayer({\r\n  id: \"satellite-mosaic-layer\",\r\n  type: \"raster\",\r\n  source: \"satellite-mosaic\"\r\n});<\/code><\/pre>\n<p>For Leaflet, use the same tile URL template with <code>L.tileLayer()<\/code> and set the required attribution, zoom range, and tile size.<\/p>\n<p>The example assumes a catalog URL already authorized for the service. In a production application, do not blindly accept arbitrary catalog or raster URLs from public query parameters. That design can introduce server-side request forgery, unintended data access, and excessive storage costs. Prefer an application-controlled catalog identifier that maps to a fixed, allowlisted S3 object.<\/p>\n<h2><span class=\"ez-toc-section\" id=\"5_Step_Four_Add_CloudFront_Caching_and_Optimize_Request_Costs\"><\/span>5. Step Four: Add CloudFront Caching and Optimize Request Costs<span class=\"ez-toc-section-end\"><\/span><\/h2>\n<p>Dynamic rendering eliminates the need to precompute every tile, but it does not make raster reads or computation free. A request can cause multiple S3 range reads, asset-selection operations, raster reprojection, resampling, and image encoding.<\/p>\n<p>CloudFront should therefore be considered a core component of the serving path, not an optional finishing touch.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"51_Cache_the_final_rendered_tile\"><\/span>5.1 Cache the final rendered tile<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>Configure a CloudFront distribution with API Gateway as its origin and expose a stable custom hostname such as <code>tiles.example.com<\/code>.<\/p>\n<p>For public, repeatable imagery, set suitable <code>Cache-Control<\/code> headers on responses. For example:<\/p>\n<pre><code>Cache-Control: public, max-age=3600, s-maxage=86400\r\nContent-Type: image\/png<\/code><\/pre>\n<p>These values are illustrative; select the freshness period based on your publication and update policy. For immutable, versioned catalogs, much longer lifetimes may be appropriate.<\/p>\n<p>A cache hit serves the previously rendered image without rerunning the full Lambda rendering operation. Consequently, it can reduce Lambda invocations, upstream S3 range reads, and response latency.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"52_Build_a_cache_key_that_matches_rendering_behavior\"><\/span>5.2 Build a cache key that matches rendering behavior<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>The cache key must distinguish requests that produce different pixels. A typical key may include:<\/p>\n<ul>\n<li>Tile path, including the matrix set and <code>z\/x\/y<\/code> coordinates.<\/li>\n<li>Catalog or mosaic identifier.<\/li>\n<li>Band selection or raster expression, if supported by the configured endpoint.<\/li>\n<li>Rendering parameters such as color map, rescaling, or image format.<\/li>\n<\/ul>\n<p>Avoid including parameters that do not change the response, because they fragment the cache unnecessarily. AWS documents these trade-offs in its <a href=\"https:\/\/docs.aws.amazon.com\/AmazonCloudFront\/latest\/DeveloperGuide\/cache-key-understand-cache-policy.html\" target=\"_blank\" rel=\"noopener\">CloudFront cache policy guide<\/a>.<\/p>\n<p>The most robust design replaces arbitrary catalog URLs with stable IDs, for example:<\/p>\n<pre><code>\/tiles\/sentinel2-oct-2026\/{z}\/{x}\/{y}.png\r\n\/tiles\/ndvi-oct-2026\/{z}\/{x}\/{y}.png<\/code><\/pre>\n<p>An application-controlled route resolves each ID to a specific catalog and an approved rendering configuration. This both simplifies the cache key and limits the ways a client can request data.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"53_Version_the_catalog_instead_of_overwriting_it\"><\/span>5.3 Version the catalog instead of overwriting it<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>Suppose a catalog initially references 200 scenes and is later updated with 15 new acquisitions. If the catalog is overwritten at the same URL, previously cached tiles may remain visible until their TTL expires or the relevant cache entries are invalidated.<\/p>\n<p>Publish the new catalog under a new versioned identifier and route new requests to that version. This provides predictable cache behavior and a practical rollback mechanism.<\/p>\n<p>For frequently updated collections, use a controlled alias such as <code>latest<\/code> only at the application or catalog-resolution layer. Keep the underlying published catalog immutable.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"54_Measure_where_costs_originate\"><\/span>5.4 Measure where costs originate<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>CloudFront cache-hit ratio alone is not sufficient. Track the full request path:<\/p>\n<table>\n<tbody>\n<tr>\n<th>Metric<\/th>\n<th>Why it matters<\/th>\n<\/tr>\n<tr>\n<td>CloudFront cache-hit ratio<\/td>\n<td>Indicates how much traffic avoids the origin<\/td>\n<\/tr>\n<tr>\n<td>API Gateway latency and errors<\/td>\n<td>Reveals request-routing problems<\/td>\n<\/tr>\n<tr>\n<td>Lambda duration and cold starts<\/td>\n<td>Measures rendering overhead<\/td>\n<\/tr>\n<tr>\n<td>Lambda concurrency and throttles<\/td>\n<td>Indicates capacity constraints<\/td>\n<\/tr>\n<tr>\n<td>S3 request volume and data transfer<\/td>\n<td>Helps identify range-read costs<\/td>\n<\/tr>\n<tr>\n<td>Tile response size<\/td>\n<td>Influences delivery and cache efficiency<\/td>\n<\/tr>\n<tr>\n<td>Catalog lookup latency<\/td>\n<td>Exposes indexing or metadata bottlenecks<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<p>The OGC COG access model depends on working HTTP range requests. If COGs are accessed through HTTP URLs or a CDN, validate range behavior and response headers. If using <code>s3:\/\/<\/code> paths with GDAL&#8217;s S3 support, verify the AWS identity, region, and object permissions in the Lambda environment.<\/p>\n<p>See the <a href=\"https:\/\/docs.ogc.org\/is\/21-026\/21-026.html\" target=\"_blank\" rel=\"noopener\">OGC COG range-request requirements<\/a> for the underlying access model.<\/p>\n<h2><span class=\"ez-toc-section\" id=\"6_Production_Engineering_Security_Performance_and_Reliability\"><\/span>6. Production Engineering: Security, Performance, and Reliability<span class=\"ez-toc-section-end\"><\/span><\/h2>\n<p>A successful prototype demonstrates that the service can render an image. An enterprise implementation must also control the amount of work each request can trigger.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"61_Restrict_data_access\"><\/span>6.1 Restrict data access<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>Keep source imagery private when public access is not necessary. Use the Lambda execution role for direct S3 access, least-privilege policies, and encryption appropriate to the dataset.<\/p>\n<p>Do not allow anonymous users to specify arbitrary raster URIs, unrestricted band expressions, or arbitrary upstream URLs without validation. Apply authentication, authorization, rate limits, and an allowlist of supported products and rendering parameters.<\/p>\n<p>If different customers have different data entitlements, do not share cached responses across access boundaries unless the cache policy and authorization design explicitly guarantee that the cached object is safe for every recipient.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"62_Tune_for_raster_workloads\"><\/span>6.2 Tune for raster workloads<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>Raster rendering is often CPU-intensive. Benchmark Lambda memory sizes and architectures against representative requests, including dense urban scenes, large multi-scene overlaps, and tiles near the edge of a coverage footprint.<\/p>\n<p>Useful optimizations include:<\/p>\n<ul>\n<li>Precompute COG overviews using appropriate resampling methods.<\/li>\n<li>Eliminate invalid or duplicate assets during ingestion.<\/li>\n<li>Limit candidate imagery through catalog boundaries and indexes.<\/li>\n<li>Set realistic concurrency limits to protect downstream services.<\/li>\n<li>Keep dependencies and container images reproducible.<\/li>\n<li>Cache stable metadata and rendered tiles where freshness rules permit.<\/li>\n<\/ul>\n<p>Do not assume that a serverless design automatically scales without constraint. Rapid traffic spikes can increase concurrent renders and S3 access volume. Establish concurrency, throttling, and error budgets using load tests.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"63_Make_mosaicking_semantics_explicit\"><\/span>6.3 Make mosaicking semantics explicit<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>A mosaic is not necessarily a scientific composite. The output may depend on the selected assets, their priority, overlap behavior, NoData handling, and the sequence in which pixels are read.<\/p>\n<p>For normalized difference vegetation index (NDVI), for example, the expression is commonly:<\/p>\n<p>[<br \/>\nNDVI=\\frac{NIR-Red}{NIR+Red}<br \/>\n]<\/p>\n<p>But producing reliable NDVI requires consistent band definitions, calibration, scale\/offset interpretation, and handling for invalid or zero denominators.<\/p>\n<p>TiTiler supports raster algorithms and configurable rendering through its available endpoints and application extensions. Confirm that the selected endpoint exposes the necessary operations before designing the client contract. If a particular scientific composite requires complex temporal ranking, cloud masking, or multiple processing stages, prepare that analytical layer upstream rather than expecting basic tile rendering to perform every operation automatically.<\/p>\n<h3><span class=\"ez-toc-section\" id=\"64_Plan_for_failure_and_observability\"><\/span>6.4 Plan for failure and observability<span class=\"ez-toc-section-end\"><\/span><\/h3>\n<p>Use structured logs and attach a request or correlation identifier to each stage. Monitor latency percentiles, error categories, cache misses, throttles, and upstream storage failures.<\/p>\n<p>Common failure patterns include:<\/p>\n<ul>\n<li><strong>No tiles appear:<\/strong> Verify tile coordinates, bounds, zoom range, CRS, CORS, and API routing.<\/li>\n<li><strong>Access denied:<\/strong> Check the Lambda role, bucket policy, encryption-key permissions, and catalog object access.<\/li>\n<li><strong>Slow initial requests:<\/strong> Profile cold starts, package import time, remote asset metadata reads, and first-request behavior.<\/li>\n<li><strong>Unexpected mosaic pixels:<\/strong> Inspect catalog membership, overlap priorities, NoData handling, band mapping, and source metadata.<\/li>\n<li><strong>High request costs:<\/strong> Look for poor cache hits, unnecessarily broad catalogs, repeated metadata discovery, and excessive overlap among source assets.<\/li>\n<\/ul>\n<p>Use repeatable test fixtures and a small set of known locations with expected render results. This provides a regression test every time TiTiler, Rasterio, GDAL, or the source imagery changes.<\/p>\n<h2><span class=\"ez-toc-section\" id=\"7_SEO_Interlinking_and_Related_Architecture_Guides\"><\/span>7. SEO Interlinking and Related Architecture Guides<span class=\"ez-toc-section-end\"><\/span><\/h2>\n<p>This implementation fits within a broader cloud-native geospatial data platform. Link the guide to related technical content that explains the upstream discovery process, data lakehouse, and map delivery layer.<\/p>\n<p>Recommended internal-link placements:<\/p>\n<ul>\n<li><strong>STAC API satellite pipelines:<\/strong> Link from the MosaicJSON generation section to a tutorial on discovering and filtering satellite scenes by acquisition date, footprint, and quality metadata. Suggested slug: <code>\/stac-api-satellite-pipelines\/<\/code><\/li>\n<li><strong>GeoParquet spatial data lakehouses:<\/strong> Link from the manifest and metadata discussion to a guide on querying geospatial metadata and vector footprints in cloud object storage. Suggested slug: <code>\/query-geoparquet-spatial-data-lakehouse\/<\/code><\/li>\n<li><strong>Web mapping performance optimization:<\/strong> Link from the CloudFront section to a guide on raster tile caching, client-side layer loading, and responsive map rendering. Suggested slug: <code>\/web-mapping-performance-optimization\/<\/code><\/li>\n<\/ul>\n<p>These are suggested internal slugs, not verified existing pages. Replace them with the site&#8217;s actual published URLs before publication.<\/p>\n<p>For external references, prioritize the official TiTiler, <code>cogeo-mosaic<\/code>, AWS Lambda, CloudFront, and OGC documentation cited in this guide.<\/p>\n<h2><span class=\"ez-toc-section\" id=\"Summary_and_Enterprise_Takeaways\"><\/span>Summary and Enterprise Takeaways<span class=\"ez-toc-section-end\"><\/span><\/h2>\n<p>A serverless COG dynamic mosaicing service combines object storage, spatial indexing, on-demand raster rendering, and edge caching into one delivery architecture.<\/p>\n<p>The essential design decisions are to keep COGs valid and efficiently organized, generate MosaicJSON catalogs in a separate ingestion workflow, deploy a reproducible TiTiler container to Lambda, expose controlled endpoints through API Gateway, and cache rendered images using a key that accurately reflects the requested output.<\/p>\n<p>The most important enterprise principle is to separate <strong>asset discovery, catalog publication, pixel processing, and tile delivery<\/strong>. That separation improves security, debugging, reproducibility, and operational control.<\/p>\n<p>Serverless COG Dynamic Mosaicing TiTiler AWS Lambda is a strong fit for variable-demand raster services with substantial opportunities for cache reuse. However, continuously high traffic, computationally intensive analytics, large temporal composites, and strict latency requirements may justify evaluating a persistent container service alongside Lambda.<\/p>\n<p>The right architecture is the one that meets the application&#8217;s latency, consistency, access-control, and cost targets under realistic workloads\u2014not simply the one that eliminates server management.<\/p>\n<p>Ready to eliminate traditional tile-rendering bottlenecks and scale your spatial infrastructure? <a href=\"https:\/\/helpwithmygisassignment.com\/\">Reach out for expert guidance<\/a> and professional project support to master your own <a href=\"https:\/\/helpwithmygisassignment.com\/blog\/?p=1768&amp;preview=true\"><b data-path-to-node=\"2,0\" data-index-in-node=\"180\">Serverless COG Dynamic Mosaicing TiTiler AWS Lambda<\/b><\/a> architecture today, and discover how custom geospatial automation can transform your web mapping applications.<\/p>\n<p><a href=\"https:\/\/helpwithmygisassignment.com\/\"><img loading=\"lazy\" decoding=\"async\" class=\"alignnone\" src=\"https:\/\/encrypted-tbn0.gstatic.com\/images?q=tbn:ANd9GcSQ1hJvYB4LQwzPdGqHar_95iJhH8wKH3kjj9Kk14kkCQ&amp;s=10\" alt=\"Call To Action Rubber Stamp. Red Call To Action Rubber Grunge Stamp Seal Vector Illustration 20312608 Vector Art at Vecteezy\" width=\"701\" height=\"436\" \/><\/a><\/p>\n","protected":false},"excerpt":{"rendered":"<p>Building a Serverless Cloud-Optimized GeoTIFF (COG) Dynamic Mosaicing Pipeline with AWS Lambda and TiTiler Introduction Pre-rendering an XYZ tile pyramid has traditionally been a practical way to publish satellite imagery to web mapping applications. However, maintaining static tile pyramids becomes increasingly expensive when a platform manages millions of raster scenes, multiple acquisition dates, overlapping satellite &#8230; <a title=\"Building a Serverless Cloud-Optimized GeoTIFF (COG) Dynamic Mosaicing Pipeline with AWS Lambda and TiTiler\" class=\"read-more\" href=\"https:\/\/helpwithmygisassignment.com\/blog\/serverless-cog-dynamic-mosaicing-titiler-aws-lambda\/\" aria-label=\"Read more about Building a Serverless Cloud-Optimized GeoTIFF (COG) Dynamic Mosaicing Pipeline with AWS Lambda and TiTiler\">Read more<\/a><\/p>\n","protected":false},"author":1,"featured_media":1872,"comment_status":"closed","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[1,4],"tags":[],"class_list":["post-1768","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-uncategorized","category-gis-articles"],"_links":{"self":[{"href":"https:\/\/helpwithmygisassignment.com\/blog\/wp-json\/wp\/v2\/posts\/1768","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/helpwithmygisassignment.com\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/helpwithmygisassignment.com\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/helpwithmygisassignment.com\/blog\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/helpwithmygisassignment.com\/blog\/wp-json\/wp\/v2\/comments?post=1768"}],"version-history":[{"count":4,"href":"https:\/\/helpwithmygisassignment.com\/blog\/wp-json\/wp\/v2\/posts\/1768\/revisions"}],"predecessor-version":[{"id":1875,"href":"https:\/\/helpwithmygisassignment.com\/blog\/wp-json\/wp\/v2\/posts\/1768\/revisions\/1875"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/helpwithmygisassignment.com\/blog\/wp-json\/wp\/v2\/media\/1872"}],"wp:attachment":[{"href":"https:\/\/helpwithmygisassignment.com\/blog\/wp-json\/wp\/v2\/media?parent=1768"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/helpwithmygisassignment.com\/blog\/wp-json\/wp\/v2\/categories?post=1768"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/helpwithmygisassignment.com\/blog\/wp-json\/wp\/v2\/tags?post=1768"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}