From 37dd4dfecdc1e79269825ac6786e80c73e4f775b Mon Sep 17 00:00:00 2001 From: Pete Gadomski Date: Fri, 21 Jun 2024 08:01:06 -0700 Subject: [PATCH] feat: add eo extension --- stac/CHANGELOG.md | 1 + stac/examples/eo/item.json | 150 +++++++++++++++++++++++++ stac/src/extensions/electro_optical.rs | 82 ++++++++++++++ stac/src/extensions/mod.rs | 3 +- 4 files changed, 235 insertions(+), 1 deletion(-) create mode 100644 stac/examples/eo/item.json create mode 100644 stac/src/extensions/electro_optical.rs diff --git a/stac/CHANGELOG.md b/stac/CHANGELOG.md index 491d8ad3..f2d2ab76 100644 --- a/stac/CHANGELOG.md +++ b/stac/CHANGELOG.md @@ -12,6 +12,7 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/), - `TryFrom` and `TryInto` for `Item` ([#255](https://github.com/stac-utils/stac-rs/pull/255)) - `wkb` feature and `GeoparquetItem` ([#260](https://github.com/stac-utils/stac-rs/pull/260), [#263](https://github.com/stac-utils/stac-rs/pull/263)) - Authentication extension ([#268](https://github.com/stac-utils/stac-rs/pull/268)) +- Electro-Optical extension ([#271](https://github.com/stac-utils/stac-rs/pull/271)) ### Fixed diff --git a/stac/examples/eo/item.json b/stac/examples/eo/item.json new file mode 100644 index 00000000..4c61901f --- /dev/null +++ b/stac/examples/eo/item.json @@ -0,0 +1,150 @@ +{ + "stac_version": "1.0.0", + "stac_extensions": [ + "https://stac-extensions.github.io/eo/v1.1.0/schema.json" + ], + "type": "Feature", + "id": "20201211_223832_CS2", + "bbox": [ + 172.91173669923782, + 1.3438851951615003, + 172.95469614953714, + 1.3690476620161975 + ], + "geometry": { + "type": "Polygon", + "coordinates": [ + [ + [ + 172.91173669923782, + 1.3438851951615003 + ], + [ + 172.95469614953714, + 1.3438851951615003 + ], + [ + 172.95469614953714, + 1.3690476620161975 + ], + [ + 172.91173669923782, + 1.3690476620161975 + ], + [ + 172.91173669923782, + 1.3438851951615003 + ] + ] + ] + }, + "properties": { + "datetime": "2020-12-11T22:38:32.125Z", + "created": "2020-12-12T01:48:13.725Z", + "updated": "2020-12-12T01:48:13.725Z", + "platform": "cool_sat2", + "instruments": [ + "cool_sensor_v1" + ], + "gsd": 0.66, + "eo:cloud_cover": 1.2, + "eo:snow_cover": 0 + }, + "collection": "eo-collection", + "links": [ + { + "rel": "root", + "href": "./collection.json", + "type": "application/json", + "title": "Simple Example Collection" + }, + { + "rel": "parent", + "href": "./collection.json", + "type": "application/json", + "title": "Simple Example Collection" + }, + { + "rel": "collection", + "href": "./collection.json", + "type": "application/json", + "title": "Simple Example Collection" + } + ], + "assets": { + "analytic": { + "href": "https://storage.googleapis.com/open-cogs/stac-examples/20201211_223832_CS2_analytic.tif", + "type": "image/tiff; application=geotiff; profile=cloud-optimized", + "title": "4-Band Analytic", + "roles": [ + "data" + ], + "eo:bands": [ + { + "name": "band1", + "common_name": "blue", + "center_wavelength": 0.47, + "full_width_half_max": 0.07, + "solar_illumination": 1959.66 + }, + { + "name": "band2", + "common_name": "green", + "center_wavelength": 0.56, + "full_width_half_max": 0.08, + "solar_illumination": 1823.24 + }, + { + "name": "band3", + "common_name": "red", + "center_wavelength": 0.645, + "full_width_half_max": 0.09, + "solar_illumination": 1512.06 + }, + { + "name": "band4", + "common_name": "nir", + "center_wavelength": 0.8, + "full_width_half_max": 0.152, + "solar_illumination": 1041.63 + } + ] + }, + "thumbnail": { + "href": "https://storage.googleapis.com/open-cogs/stac-examples/20201211_223832_CS2.jpg", + "title": "Thumbnail", + "type": "image/png", + "roles": [ + "thumbnail" + ] + }, + "visual": { + "href": "https://storage.googleapis.com/open-cogs/stac-examples/20201211_223832_CS2.tif", + "type": "image/tiff; application=geotiff; profile=cloud-optimized", + "title": "3-Band Visual", + "roles": [ + "visual" + ], + "eo:bands": [ + { + "name": "band3", + "common_name": "red", + "center_wavelength": 0.645, + "full_width_half_max": 0.09 + }, + { + "name": "band2", + "common_name": "green", + "center_wavelength": 0.56, + "full_width_half_max": 0.08 + }, + { + "name": "band1", + "common_name": "blue", + "center_wavelength": 0.47, + "full_width_half_max": 0.07 + } + ] + } + } +} diff --git a/stac/src/extensions/electro_optical.rs b/stac/src/extensions/electro_optical.rs new file mode 100644 index 00000000..87b29419 --- /dev/null +++ b/stac/src/extensions/electro_optical.rs @@ -0,0 +1,82 @@ +//! The [electro-optical](https://github.com/stac-extensions/eo) extension. + +use crate::Extension; +use serde::{Deserialize, Serialize}; + +/// EO data is considered to be data that represents a snapshot of the Earth for +/// a single date and time. +/// +/// It could consist of multiple spectral bands in any part of the +/// electromagnetic spectrum. Examples of EO data include sensors with visible, +/// short-wave and mid-wave IR bands (e.g., the OLI instrument on Landsat-8), +/// long-wave IR bands (e.g. TIRS aboard Landsat-8). +#[derive(Debug, Serialize, Deserialize)] +pub struct ElectroOptical { + /// An array of available bands where each object is a [Band]. + /// + /// If given, requires at least one band. + #[serde(skip_serializing_if = "Vec::is_empty", default)] + pub bands: Vec, + + /// Estimate of cloud cover, in %. + #[serde(skip_serializing_if = "Option::is_none")] + pub cloud_cover: Option, + + /// Estimate of snow and ice cover, in %. + #[serde(skip_serializing_if = "Option::is_none")] + pub snow_cover: Option, +} + +/// [Spectral +/// bands](https://www.sciencedirect.com/topics/earth-and-planetary-sciences/spectral-band) +/// in an [Asset](crate::Asset). +#[derive(Debug, Serialize, Deserialize)] +pub struct Band { + /// The name of the band (e.g., "B01", "B8", "band2", "red"). + #[serde(skip_serializing_if = "Option::is_none")] + pub name: Option, + + /// The name commonly used to refer to the band to make it easier to search for bands across instruments. + /// + /// See the list of [accepted common names](https://github.com/stac-extensions/eo#common-band-names). + #[serde(skip_serializing_if = "Option::is_none")] + pub common_name: Option, + + /// Description to fully explain the band. + /// + /// [CommonMark 0.29](http://commonmark.org/) syntax MAY be used for rich text representation. + #[serde(skip_serializing_if = "Option::is_none")] + pub description: Option, + + /// The center wavelength of the band, in micrometers (μm). + #[serde(skip_serializing_if = "Option::is_none")] + pub center_wavelength: Option, + + /// Full width at half maximum (FWHM). + /// + /// The width of the band, as measured at half the maximum transmission, in + /// micrometers (μm). + #[serde(skip_serializing_if = "Option::is_none")] + pub full_width_half_max: Option, + + /// The solar illumination of the band, as measured at half the maximum transmission, in W/m2/micrometers. + #[serde(skip_serializing_if = "Option::is_none")] + pub solar_illumination: Option, +} + +impl Extension for ElectroOptical { + const IDENTIFIER: &'static str = "https://stac-extensions.github.io/eo/v1.1.0/schema.json"; + const PREFIX: &'static str = "eo"; +} + +#[cfg(test)] +mod tests { + use super::ElectroOptical; + use crate::{Extensions, Item}; + + #[test] + fn item() { + let item: Item = crate::read("examples/eo/item.json").unwrap(); + let _: ElectroOptical = item.extension().unwrap().unwrap(); + } +} diff --git a/stac/src/extensions/mod.rs b/stac/src/extensions/mod.rs index 1ad52054..58faf17c 100644 --- a/stac/src/extensions/mod.rs +++ b/stac/src/extensions/mod.rs @@ -11,7 +11,7 @@ //! | Extension | Maturity | **stac-rs** supported version | //! | -- | -- | -- | //! | [Authentication](https://github.com/stac-extensions/authentication) | Proposal | v1.1.0 | -//! | [Electro-Optical](https://github.com/stac-extensions/eo) | Stable | n/a | +//! | [Electro-Optical](https://github.com/stac-extensions/eo) | Stable | v1.1.0 | //! | [File Info](https://github.com/stac-extensions/file) | Stable | n/a | //! | [Landsat](https://github.com/stac-extensions/landsat) | Stable | n/a | //! | [Projection](https://github.com/stac-extensions/projection) | Stable | v1.1.0 | @@ -44,6 +44,7 @@ //! ``` pub mod authentication; +pub mod electro_optical; pub mod projection; pub mod raster;