From 4774ea97f507e92d4adcde031f67e668f4d6d57a Mon Sep 17 00:00:00 2001 From: ValentinaHutter Date: Wed, 19 Nov 2025 09:34:39 +0100 Subject: [PATCH 1/3] update descriptions, use Sentinel2_L2A --- .../benchmark_scenarios/sen2like.json | 31 ++++ .../eodc/sen2like/openeo_udp/README.md | 17 ++ .../eodc/sen2like/openeo_udp/generate.py | 72 ++++++++ .../eodc/sen2like/openeo_udp/sen2like.json | 171 ++++++++++++++++++ .../eodc/sen2like/records/sen2like.json | 104 +++++++++++ 5 files changed, 395 insertions(+) create mode 100644 algorithm_catalog/eodc/sen2like/benchmark_scenarios/sen2like.json create mode 100644 algorithm_catalog/eodc/sen2like/openeo_udp/README.md create mode 100644 algorithm_catalog/eodc/sen2like/openeo_udp/generate.py create mode 100644 algorithm_catalog/eodc/sen2like/openeo_udp/sen2like.json create mode 100644 algorithm_catalog/eodc/sen2like/records/sen2like.json diff --git a/algorithm_catalog/eodc/sen2like/benchmark_scenarios/sen2like.json b/algorithm_catalog/eodc/sen2like/benchmark_scenarios/sen2like.json new file mode 100644 index 00000000..be959f3c --- /dev/null +++ b/algorithm_catalog/eodc/sen2like/benchmark_scenarios/sen2like.json @@ -0,0 +1,31 @@ +[ + { + "id": "sen2like", + "type": "openeo", + "description": "Sen2like test", + "backend": "https://openeo.eodc.eu/openeo/1.2.0", + "process_graph": { + "ardsen2like": { + "process_id": "sen2like", + "namespace": "https://raw.githubusercontent.com/ESA-APEx/apex_algorithms/refs/heads/sen2like/algorithm_catalog/eodc/sen2like/openeo_udp/sen2like.json", + "arguments": { + "bbox": { + "east": 16.414, + "north": 48.008, + "south": 47.962, + "west": 16.342 + }, + "temporal_extent": [ + "2023-05-01", + "2023-05-30" + ] + }, + "result": true + } + }, + "reference_data": { + }, + "reference_options": { + } + } +] \ No newline at end of file diff --git a/algorithm_catalog/eodc/sen2like/openeo_udp/README.md b/algorithm_catalog/eodc/sen2like/openeo_udp/README.md new file mode 100644 index 00000000..f16d5531 --- /dev/null +++ b/algorithm_catalog/eodc/sen2like/openeo_udp/README.md @@ -0,0 +1,17 @@ +# Sen2like + +The Sen2Like processor was developed by ESA as part of the EU Copernicus program. It creates Sentinel-2 like harmonized (Level-2H) or fused (Level-2F) surface reflectances by harmonizing Sentinel-2 and Landsat 8/Landsat 9 to increase the temporal revisits. The fusion involves the upscaling of Landsat 8/Landsat 9 data to Sentinel-2 resolution. Furthermore, the resulting sen2like L2H/ L2F data can be processed using openEO to generate statistics, vegetation indices, do comparisons with other datasets, etc. + +### Methodology + +The processing of the incoming Landsat and Sentinel-2 L1C data includes the following main processing steps: Geometric Processing, Stitching, Geometric Check, Inter-calibration, Atmospheric correction, BRDF Adjustment, SBAF, Topographic Correction, Data Fusion. If Sentinel-2 L2A data is provided, sen2like processing will not include Atmospheric and Topographic Correction. In the geometric processing step, the input images are co-registered to a Sentinel-2 reference image. The atmospheric correction step makes use of the sen2cor processor and additionally relies on Copernicus Atmosphere Monitoring Service (CAMS) Near Real Time and Reanalysis data as well as the Copernicus Digital Elevation Model. The Data Fusion step alignes Landsat 8 image pixel spacing fully with Sentinel2 image pixel spacing. Depending on the band, the resolution of the Landsat L2F product is 10 m, 20 m or 30 m. + +### Quality + +The geometric check process is a Quality Control step of the product. For further information, see Sen2like User Manual. + +### Links + +- [RD1] openEO platform Sen2like documentation https://docs.openeo.cloud/usecases/ard/sen2like + +- [RD1] Saunier, S. (2025). Sen2like User Manual https://github.com/senbox-org/sen2like/blob/master/sen2like/docs/source/S2-SEN2LIKE-UM-V1.10.pdf" \ No newline at end of file diff --git a/algorithm_catalog/eodc/sen2like/openeo_udp/generate.py b/algorithm_catalog/eodc/sen2like/openeo_udp/generate.py new file mode 100644 index 00000000..32aec2a8 --- /dev/null +++ b/algorithm_catalog/eodc/sen2like/openeo_udp/generate.py @@ -0,0 +1,72 @@ +import json +from pathlib import Path + +import openeo +from openeo.api.process import Parameter +from openeo.rest._datacube import THIS +from openeo.rest.udp import build_process_dict + +def generate(): + connection = openeo.connect("https://openeo.eodc.eu/openeo/1.2.0/").authenticate_oidc() + + spatial_extent = Parameter.spatial_extent( + name="spatial_extent", + description="Limits the data to process to the specified bounding box or polygons.\\n\\nFor raster data, the process loads the pixel into the data cube if the point at the pixel center intersects with the bounding box or any of the polygons (as defined in the Simple Features standard by the OGC).\\nFor vector data, the process loads the geometry into the data cube if the geometry is fully within the bounding box or any of the polygons (as defined in the Simple Features standard by the OGC). Empty geometries may only be in the data cube if no spatial extent has been provided.\\n\\nEmpty geometries are ignored.\\nSet this parameter to null to set no limit for the spatial extent." + ) + + temporal_extent = Parameter.temporal_interval( + name="temporal_extent", + description="Temporal extent specified as two-element array with start and end date/date-time." + ) + + schema = { + "type": "string", + "enum": ["B01", "B02", "B03", "B04", "B05", "B06", "B07", "B08", "B8A", "B11", "B12"], + } + bands = Parameter.array( + name="bands", + description="Sentinel-2 bands to include in the composite.", + item_schema=schema, + default=["B04", "B03", "B02"], + optional=True, + ) + + collection = 'SENTINEL2_L2A' + + s2_l1c = connection.load_collection( + collection, + spatial_extent=spatial_extent, + temporal_extent=temporal_extent, + bands=bands) + + sen2like = s2_l1c.process('sen2like', { + 'data': THIS, + 'target_product': 'L2F', + 'export_original_files': True, + 'cloud_cover': 50}) + + returns = { + "description": "A data cube with the newly computed values.\n\nThe result will combine Sentinel-2 and Landsat timesteps for the requested extent. Just like Sentinel 2 data, sen2like generates .SAFE output files, which are zipped for the purpose of openEO. For both Landsat and Sentinel acquisitions the .SAFE files include the requested bands. Note, that the sen2like Landsat outputs do not include equivalents of Sentinel-2 bands B05, B06, B07.", + "schema": { + "type": "object", + "subtype": "datacube" + } + } + + return build_process_dict( + process_graph=sen2like, + process_id="sen2like", + summary="Computes a harmonzed Sentinel-2 and Landsat timeseries.", + description=(Path(__file__).parent / "README.md").read_text(), + parameters=[ + spatial_extent, + temporal_extent + ], + returns=returns, + categories=["sentinel-2", "ARD"] + ) + + +if __name__ == "__main__": + with open("sen2like.json", "w") as f: + json.dump(generate(), f, indent=2) \ No newline at end of file diff --git a/algorithm_catalog/eodc/sen2like/openeo_udp/sen2like.json b/algorithm_catalog/eodc/sen2like/openeo_udp/sen2like.json new file mode 100644 index 00000000..94a7b6f5 --- /dev/null +++ b/algorithm_catalog/eodc/sen2like/openeo_udp/sen2like.json @@ -0,0 +1,171 @@ +{ + "process_graph": { + "loadcollection1": { + "process_id": "load_collection", + "arguments": { + "bands": { + "from_parameter": "bands" + }, + "id": "SENTINEL2_L2A", + "spatial_extent": { + "from_parameter": "spatial_extent" + }, + "temporal_extent": { + "from_parameter": "temporal_extent" + } + } + }, + "sen2like1": { + "process_id": "sen2like", + "arguments": { + "cloud_cover": 50, + "data": { + "from_node": "loadcollection1" + }, + "export_original_files": true, + "target_product": "L2F" + }, + "result": true + } + }, + "id": "sen2like", + "description": "# Sen2like\n\nThe Sen2Like processor was developed by ESA as part of the EU Copernicus program. It creates Sentinel-2 like harmonized (Level-2H) or fused (Level-2F) surface reflectances by harmonizing Sentinel-2 and Landsat 8/Landsat 9 to increase the temporal revisits. Based on the resulting L2F product, multiple indices can be computed, such as the NDVI and LAI. The fusion also involves the upscaling of Landsat 8/Landsat 9 data to Sentinel-2 resolution. With the new L2F data higher time-series resolution vegetation indices (such as NDVI, LAI, FAPAR, FCOVER) can be calculated.\n\n### Methodology\n\n\n\n### Quality\n\n\n\n### Links\n\n- [RD1] openEO platform Sen2like documentation https://docs.openeo.cloud/usecases/ard/sen2like", + "parameters": [ + { + "name": "bands", + "description": "Only adds the specified bands into the data cube so that bands that don't match the list of band names are not available. Applies to all dimensions of type `bands`.\n\nEither the unique band name (metadata field `name` in bands) or one of the common band names (metadata field `common_name` in bands) can be specified. If the unique band name and the common name conflict, the unique band name has a higher priority.\n\nThe order of the specified array defines the order of the bands in the data cube. If multiple bands match a common name, all matched bands are included in the original order.\n\nIt is recommended to use this parameter instead of using ``filter_bands()`` directly after loading unbounded data.", + "schema": [ + { + "type": "array", + "minItems": 1, + "items": { + "type": "string", + "subtype": "band-name" + } + }, + { + "title": "No filter", + "description": "Don't filter bands. All bands are included in the data cube.", + "type": "null" + } + ], + "default": null, + "optional": true + }, + { + "name": "spatial_extent", + "description": "Limits the data to process to the specified bounding box or polygons.\\n\\nFor raster data, the process loads the pixel into the data cube if the point at the pixel center intersects with the bounding box or any of the polygons (as defined in the Simple Features standard by the OGC).\\nFor vector data, the process loads the geometry into the data cube if the geometry is fully within the bounding box or any of the polygons (as defined in the Simple Features standard by the OGC). Empty geometries may only be in the data cube if no spatial extent has been provided.\\n\\nEmpty geometries are ignored.\\nSet this parameter to null to set no limit for the spatial extent.", + "schema": [ + { + "title": "Bounding Box", + "type": "object", + "subtype": "bounding-box", + "required": [ + "west", + "south", + "east", + "north" + ], + "properties": { + "west": { + "description": "West (lower left corner, coordinate axis 1).", + "type": "number" + }, + "south": { + "description": "South (lower left corner, coordinate axis 2).", + "type": "number" + }, + "east": { + "description": "East (upper right corner, coordinate axis 1).", + "type": "number" + }, + "north": { + "description": "North (upper right corner, coordinate axis 2).", + "type": "number" + }, + "base": { + "description": "Base (optional, lower left corner, coordinate axis 3).", + "type": [ + "number", + "null" + ], + "default": null + }, + "height": { + "description": "Height (optional, upper right corner, coordinate axis 3).", + "type": [ + "number", + "null" + ], + "default": null + }, + "crs": { + "description": "Coordinate reference system of the extent, specified as as [EPSG code](http://www.epsg-registry.org/) or [WKT2 CRS string](http://docs.opengeospatial.org/is/18-010r7/18-010r7.html). Defaults to `4326` (EPSG code 4326) unless the client explicitly requests a different coordinate reference system.", + "anyOf": [ + { + "title": "EPSG Code", + "type": "integer", + "subtype": "epsg-code", + "minimum": 1000, + "examples": [ + 3857 + ] + }, + { + "title": "WKT2", + "type": "string", + "subtype": "wkt2-definition" + } + ], + "default": 4326 + } + } + }, + { + "title": "Vector data cube", + "description": "Limits the data cube to the bounding box of the given geometries in the vector data cube. For raster data, all pixels inside the bounding box that do not intersect with any of the polygons will be set to no data (`null`). Empty geometries are ignored.", + "type": "object", + "subtype": "datacube", + "dimensions": [ + { + "type": "geometry" + } + ] + }, + { + "title": "No filter", + "description": "Don't filter spatially. All data is included in the data cube.", + "type": "null" + } + ] + }, + { + "name": "temporal_extent", + "description": "Temporal extent specified as two-element array with start and end date/date-time.", + "schema": { + "type": "array", + "subtype": "temporal-interval", + "uniqueItems": true, + "minItems": 2, + "maxItems": 2, + "items": { + "anyOf": [ + { + "type": "string", + "subtype": "date-time", + "format": "date-time" + }, + { + "type": "string", + "subtype": "date", + "format": "date" + }, + { + "type": "null" + } + ] + } + } + } + ] +} \ No newline at end of file diff --git a/algorithm_catalog/eodc/sen2like/records/sen2like.json b/algorithm_catalog/eodc/sen2like/records/sen2like.json new file mode 100644 index 00000000..9fc0f06f --- /dev/null +++ b/algorithm_catalog/eodc/sen2like/records/sen2like.json @@ -0,0 +1,104 @@ +{ + "id": "sen2like", + "type": "Feature", + "conformsTo": [ + "http://www.opengis.net/spec/ogcapi-records-1/1.0/req/record-core", + "https://apex.esa.int/core/openeo-udp" + ], + "geometry": null, + "properties": { + "created": "2025-05-22T00:00:00Z", + "updated": "2025-05-22T00:00:00Z", + "type": "service", + "title": "Harmonized Landsat/Sentinel-2 ARD", + "description": "# Sen2like\n\nThe Sen2Like processor was developed by ESA as part of the EU Copernicus program. It creates Sentinel-2 like harmonized (Level-2H) or fused (Level-2F) surface reflectances by harmonizing Sentinel-2 and Landsat 8/Landsat 9 to increase the temporal revisits. The fusion involves the upscaling of Landsat 8/Landsat 9 data to Sentinel-2 resolution. Furthermore, the resulting sen2like L2H/ L2F data can be processed using openEO to generate statistics, vegetation indices, do comparisons with other datasets, etc.\n\n### Methodology\n\nThe processing of the incoming Landsat and Sentinel-2 L1C data includes the following main processing steps: Geometric Processing, Stitching, Geometric Check, Inter-calibration, Atmospheric correction, BRDF Adjustment, SBAF, Topographic Correction, Data Fusion. If Sentinel-2 L2A data is provided, sen2like processing will not include Atmospheric and Topographic Correction. In the geometric processing step, the input images are co-registered to a Sentinel-2 reference image. The atmospheric correction step makes use of the sen2cor processor and additionally relies on Copernicus Atmosphere Monitoring Service (CAMS) Near Real Time and Reanalysis data as well as the Copernicus Digital Elevation Model. The Data Fusion step alignes Landsat 8 image pixel spacing fully with Sentinel2 image pixel spacing. Depending on the band, the resolution of the Landsat L2F product is 10 m, 20 m or 30 m.\n\n### Quality\n\nThe geometric check process is a Quality Control step of the product. For further information, see Sen2like User Manual.\n\n### Links\n\n- [RD1] openEO platform Sen2like documentation https://docs.openeo.cloud/usecases/ard/sen2like\n- [RD1] Saunier, S. (2025). Sen2like User Manual https://github.com/senbox-org/sen2like/blob/master/sen2like/docs/source/S2-SEN2LIKE-UM-V1.10.pdf", + "cost_estimate": 0.01, + "cost_unit": "platform credits per km\u00b2", + "keywords": [ + "sentinel-2", + "landsat-8", + "ard" + ], + "language": { + "code": "en-US", + "name": "English (United States)" + }, + "languages": [ + { + "code": "en-US", + "name": "English (United States)" + } + ], + "contacts": [ + { + "name": "Valentina Hutter", + "position": "Researcher", + "organization": "EODC", + "links": [ + { + "href": "https://www.eodc.eu/", + "title": "EODC Website", + "rel": "about", + "type": "text/html" + }, + { + "href": "https://github.com/ValentinaHutter", + "title": "GitHub", + "rel": "about", + "type": "text/html" + } + ], + "contactInstructions": "Contact via EODC", + "roles": [ + "principal investigator", + "processor" + ] + } + ], + "themes": [ + { + "concepts": [ + { + "id": "Sentinel-2 MSI" + } + ], + "scheme": "https://gcmd.earthdata.nasa.gov/kms/concepts/concept_scheme/sciencekeywords" + } + ], + "formats": [ + { + "name": "SAFE" + }, + { + "name": "zip" + } + ] + }, + "linkTemplates": [], + "links": [ + { + "rel": "application", + "type": "application/vnd.openeo+json;type=process", + "title": "openEO Process Definition", + "href": "https://raw.githubusercontent.com/ESA-APEx/apex_algorithms/refs/heads/sen2like/algorithm_catalog/eodc/sen2like/openeo_udp/sen2like.json" + }, + { + "rel": "code", + "type": "text/html", + "title": "Sen2like git source repository", + "href": "https://github.com/senbox-org/sen2like" + }, + { + "rel": "service", + "type": "application/json", + "title": "openEO platform", + "href": "https://openeo.cloud" + }, + { + "rel": "cite-as", + "type": "text/html", + "title": "S. Saunier, J. Louis, V. Debaecker et al., \"Sen2like, A Tool To Generate Sentinel-2 Harmonised Surface Reflectance Products - First Results with Landsat-8,\" IGARSS 2019 - 2019 IEEE International Geoscience and Remote Sensing Symposium, Yokohama, Japan, 2019, pp. 5650-5653", + "href": "https://doi.org/10.1109/IGARSS.2019.8899213" + } + ] +} From fc19bbaeabfbef2b9bf67c5f3f1f99dddf992eb8 Mon Sep 17 00:00:00 2001 From: ValentinaHutter Date: Mon, 24 Nov 2025 11:53:32 +0100 Subject: [PATCH 2/3] update benchmark spatial_extent, cost estimate --- .../eodc/sen2like/benchmark_scenarios/sen2like.json | 2 +- algorithm_catalog/eodc/sen2like/records/sen2like.json | 2 -- 2 files changed, 1 insertion(+), 3 deletions(-) diff --git a/algorithm_catalog/eodc/sen2like/benchmark_scenarios/sen2like.json b/algorithm_catalog/eodc/sen2like/benchmark_scenarios/sen2like.json index be959f3c..617655ad 100644 --- a/algorithm_catalog/eodc/sen2like/benchmark_scenarios/sen2like.json +++ b/algorithm_catalog/eodc/sen2like/benchmark_scenarios/sen2like.json @@ -9,7 +9,7 @@ "process_id": "sen2like", "namespace": "https://raw.githubusercontent.com/ESA-APEx/apex_algorithms/refs/heads/sen2like/algorithm_catalog/eodc/sen2like/openeo_udp/sen2like.json", "arguments": { - "bbox": { + "spatial_extent": { "east": 16.414, "north": 48.008, "south": 47.962, diff --git a/algorithm_catalog/eodc/sen2like/records/sen2like.json b/algorithm_catalog/eodc/sen2like/records/sen2like.json index 9fc0f06f..3ef65512 100644 --- a/algorithm_catalog/eodc/sen2like/records/sen2like.json +++ b/algorithm_catalog/eodc/sen2like/records/sen2like.json @@ -12,8 +12,6 @@ "type": "service", "title": "Harmonized Landsat/Sentinel-2 ARD", "description": "# Sen2like\n\nThe Sen2Like processor was developed by ESA as part of the EU Copernicus program. It creates Sentinel-2 like harmonized (Level-2H) or fused (Level-2F) surface reflectances by harmonizing Sentinel-2 and Landsat 8/Landsat 9 to increase the temporal revisits. The fusion involves the upscaling of Landsat 8/Landsat 9 data to Sentinel-2 resolution. Furthermore, the resulting sen2like L2H/ L2F data can be processed using openEO to generate statistics, vegetation indices, do comparisons with other datasets, etc.\n\n### Methodology\n\nThe processing of the incoming Landsat and Sentinel-2 L1C data includes the following main processing steps: Geometric Processing, Stitching, Geometric Check, Inter-calibration, Atmospheric correction, BRDF Adjustment, SBAF, Topographic Correction, Data Fusion. If Sentinel-2 L2A data is provided, sen2like processing will not include Atmospheric and Topographic Correction. In the geometric processing step, the input images are co-registered to a Sentinel-2 reference image. The atmospheric correction step makes use of the sen2cor processor and additionally relies on Copernicus Atmosphere Monitoring Service (CAMS) Near Real Time and Reanalysis data as well as the Copernicus Digital Elevation Model. The Data Fusion step alignes Landsat 8 image pixel spacing fully with Sentinel2 image pixel spacing. Depending on the band, the resolution of the Landsat L2F product is 10 m, 20 m or 30 m.\n\n### Quality\n\nThe geometric check process is a Quality Control step of the product. For further information, see Sen2like User Manual.\n\n### Links\n\n- [RD1] openEO platform Sen2like documentation https://docs.openeo.cloud/usecases/ard/sen2like\n- [RD1] Saunier, S. (2025). Sen2like User Manual https://github.com/senbox-org/sen2like/blob/master/sen2like/docs/source/S2-SEN2LIKE-UM-V1.10.pdf", - "cost_estimate": 0.01, - "cost_unit": "platform credits per km\u00b2", "keywords": [ "sentinel-2", "landsat-8", From ba3c918abbfebfda4d74d4230fe6ddd1ea28fc1a Mon Sep 17 00:00:00 2001 From: ValentinaHutter <85164505+ValentinaHutter@users.noreply.github.com> Date: Mon, 24 Nov 2025 11:56:14 +0100 Subject: [PATCH 3/3] Update algorithm_catalog/eodc/sen2like/records/sen2like.json Co-authored-by: Jeroen Dries --- algorithm_catalog/eodc/sen2like/records/sen2like.json | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/algorithm_catalog/eodc/sen2like/records/sen2like.json b/algorithm_catalog/eodc/sen2like/records/sen2like.json index 3ef65512..8ce714cd 100644 --- a/algorithm_catalog/eodc/sen2like/records/sen2like.json +++ b/algorithm_catalog/eodc/sen2like/records/sen2like.json @@ -80,6 +80,12 @@ "title": "openEO Process Definition", "href": "https://raw.githubusercontent.com/ESA-APEx/apex_algorithms/refs/heads/sen2like/algorithm_catalog/eodc/sen2like/openeo_udp/sen2like.json" }, + { + "rel": "webapp", + "type": "text/html", + "title": "OpenEO Web Editor", + "href": "https://editor.openeo.org/?wizard=UDP&wizard%7Eprocess=sen2like&wizard%7EprocessUrl=https://raw.githubusercontent.com/ESA-APEx/apex_algorithms/refs/heads/sen2like/algorithm_catalog/eodc/sen2like/openeo_udp/sen2like.json&server=openeo.eodc.eu" + }, { "rel": "code", "type": "text/html",