easysnowdata#
easysnowdata
Snow-relevant geospatial data, one call each, as xarray.
Forty products — station observations from SNOTEL and the other AWDB networks, CDEC, BC, NVE, and Yukon; Sentinel-1 RTC, Sentinel-2, HLS, and PlanetScope imagery; MODIS and VIIRS snow cover; SNODAS and UCLA snow water equivalent and depth; the Sturm & Liston snow classes and a mountain snow mask; five DEMs, CHILI, and a hillshade; WorldCover, NLCD, and forest cover; basins; ERA5 and Köppen-Geiger climate; and the boundaries that frame them: countries, states, counties, mountain ranges, and glacier outlines — behind one API that takes an area of interest and a time range, returns lazy Dask-backed xarray objects (and GeoDataFrames for vector products), and never downloads more than it has to.
import easysnowdata as esd
aoi = (-121.94, 46.72, -121.54, 46.99) # Mount Rainier; any AOI form works
inv_gdf = esd.stations.inventory(aoi, daily_only=True) # which snow stations are here
obs_ds = esd.stations.load(inv_gdf, variables=["swe", "snwd"], time="2023-10/2024-09")
dem_da = esd.terrain.dem.load(aoi) # Copernicus GLO-30 …
dem_da = esd.terrain.dem.load(aoi, product="3dep") # … or NASADEM, SRTM, 3DEP, ALOS, GEDTM30
s1_ds = esd.sar.sentinel1.load(aoi, "2024-03", units="dB") # Sentinel-1 RTC
snodas_ds = esd.snow.snodas.load(aoi, "2024-03") # SNODAS, no account needed
counties_gdf = esd.boundaries.admin.counties(aoi) # Pierce and Lewis (US Census)
ranges_gdf = esd.boundaries.mountains.load(aoi) # GMBA mountain ranges
glaciers_gdf = esd.boundaries.glaciers.load(aoi) # RGI 7.0 (Earthdata username + password)
ax = esd.plotting.map(dem_da, cmap="terrain") # equal aspect, scale bar, graticule
esd.plotting.add_outline(ax, glaciers_gdf) # vectors in the map's CRS
esd.plotting.timeseries(obs_ds["swe"]) # calendar dates, units in [ ]
Where to go#
Installation, credentials, the concepts every loader shares, and a tour of the modules.
One executed script per product, with the figure it produces.
Every public function, grouped by subpackage.
Every product: its routes, resolution, credentials, licence, and weekly health.
Which product to use, accounts, memory, CRS, and what to do when a source is down.
The pixi tasks, the four test tiers, how to add a product, and the changelog.
Design in one paragraph#
Every loader takes the same aoi (a bounding-box tuple, a shapely geometry, a
GeoDataFrame in any CRS, or an odc.geo.GeoBox) and the same time (anything
pandas or STAC understands). Search and load are separate calls. Results are
lazy, carry their CRS on both the .rio and .odc accessors, and carry
source, license, and data_citation in .attrs — GeoDataFrames too, which
come back in EPSG:4326 holding the whole features that touch the AOI. Products with more than
one route expose them through source=, so a Planetary Computer outage is one
keyword away from an alternative. Credentials are checked before any network
request, and the error says exactly how to fix them. Processing that is one
line of xarray (a normalized difference, a threshold) is written out rather than
wrapped, so nothing about the pipeline is hidden. See Concepts
for the whole contract.
Citing#
Gagliano, E. (2024). easysnowdata [Software]. Zenodo.
https://doi.org/10.5281/zenodo.14741501
Each product also carries the citation of the data it serves in
ds.attrs["data_citation"], and the catalog page for that product repeats it.