Skip to main content
GRSdriver_icon

GRSdriver package

Driver dedicated to load and prepare data for the GRS processor

PyPI Python tests Documentation License

GRSdriver loads a Level-1 satellite image into a single xarray.Dataset ready for the GRS atmospheric and sunglint correction:

  • Sentinel-2 L1C (.SAFE): top-of-atmosphere reflectance of the selected bands on a common grid, with accurate viewing angles computed per band and per detector from the granule metadata
  • Landsat 8 and 9 Collection-2 L1: reflectance, brightness temperature of the thermal bands, sun/viewing angles and L1 quality flags
  • spectral response functions and central wavelengths of each band
  • spatial subsetting, parallel reading, lazy (dask) loading and low memory options for full tiles
  • visualization tools

Full documentation: https://grsdriver.readthedocs.io

What's new in 2.0

  • pip-only install: EOReader and the GDAL Python bindings are no longer needed.
  • ~2x faster: full Sentinel-2 tile at 20 m in ~30 s (bands read and angles computed in parallel), fully lazy dask mode in ~20 s.
  • Fixes: Sentinel-2 angles of processing baselines < 4.0, alignment of the Landsat panchromatic band, size of the SpatioTemp boxes.
  • Upgrading from 1.x: the drivers no longer take **kwargs (they were passed to EOReader) and have no .reader attribute; a subset given as a sequence is a bounding box (minx, miny, maxx, maxy) in the product CRS. See the CHANGELOG.

Installation

Python 3.9 to 3.13:

pip install GRSdriver

No separate GDAL installation is needed: rasterio and geopandas ship with their own GDAL (including the JPEG2000 driver for Sentinel-2). Optional extras:

Extra For Install
cli grs_driver command line (RGB quicklooks) pip install "GRSdriver[cli]"
viz interactive visualization tools (GRSdriver.visual) pip install "GRSdriver[viz]"
tutorials running the tutorial notebooks pip install "GRSdriver[tutorials]"

From the repository

To run the tutorials or work on the code:

git clone https://github.com/Tristanovsk/GRSdriver.git
cd GRSdriver
pip install -e ".[cli,viz,tutorials,dev]"

or with conda: conda env create -f environment.yml && conda activate grsdriver.

Quick start

from GRSdriver import Sentinel2Driver, LandsatDriver

# Sentinel-2: 20 m bands, viewing angles computed on a 60 m grid
l1c = Sentinel2Driver('S2B_MSIL1C_..._.SAFE', resolution=20)
l1c.load_product()
prod = l1c.prod          # bands, vza, raa, sza, SRF, wl_true + metadata

# Landsat 8/9
l1 = LandsatDriver('LC09_L1TP_..._02_T1', resolution=30)
l1.load_product()

# region of interest: any geometry (GeoSeries, any CRS), here a lon/lat box
import geopandas as gpd
from shapely.geometry import box
roi = gpd.GeoSeries([box(5.0, 43.38, 5.25, 43.58)], crs=4326)
l1c = Sentinel2Driver('S2B_MSIL1C_..._.SAFE', resolution=20, subset=roi)

The bands are read by 4 threads in parallel: set n_workers (e.g. n_workers=1) to trade speed for memory. For a full Sentinel-2 tile at 10 m, Sentinel2Driver(..., lazy_geom=True) keeps the per-band viewing angles lazy and saves several GB of memory. Set GRSDRIVER_USE_DASK=1 before importing GRSdriver to get a fully lazy (dask-backed) product.

Command line

grs_driver writes an RGB quicklook (PNG) of a Sentinel-2 or Landsat product:

grs_driver S2B_MSIL1C_..._.SAFE --odir ./quicklooks --resolution 60

Tutorials

The notebooks are in docs/source/tutorials/ and rendered with their outputs in the documentation:

Notebook Content
GRSdriver_basics load a Sentinel-2 L1C image, geometry, RGB, NDWI water mask
GRSdriver_subsetting subset a time series of images and build a datacube
GRSdriver_landsat9_TIR Landsat 9 with its thermal bands
GRSdriver_landsat9_L1_CAMS Landsat 9 with CAMS atmospheric data
sentinel2_download download Sentinel-2 L1C images

The paths to the images are those of the author's machine: set them to your own data. See Updating the tutorials to rerun them for the documentation.

Sentinel-2 viewing geometry

The MSI swath is covered by 12 staggered detectors: odd and even detectors look in opposite directions, and the bands of a detector are shifted in the focal plane. Each band therefore has its own viewing angles, with jumps at the detector borders. GRSdriver computes them per band and per detector from the L1C metadata (see Methods).

RGB image

Over water, sunglint is so directional that its reflectance changes abruptly at the detector borders: here +23 % in B11 (1610 nm) between detectors 10 and 11 (right: viewing azimuth). These stripes are a property of the target, not an artifact, and their size depends on the sea roughness, i.e. on the wind speed (Fougnie et al., 2016; Harmel et al., 2018):

sunglint at detector borders

Viewing azimuth of each band computed by GRSdriver:

viewing azimuth per band

across-track profile

Example

example gif

2D-fitting method for angle computation

example files example files example files

Example of water masking

example files

Changes and contributing

See the CHANGELOG. Tests run with pytest tests (the tests that need satellite products are skipped when they are not available); the contributing guide explains how to update the tutorials and make a release.

Metadata

Release files for GRSdriver 2.0.3

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for GRSdriver 2.0.3
File Size Uploaded
grsdriver-2.0.3.tar.gz 1.7 MB Details

Built distribution (wheel)

Table of built distributions (wheels) for GRSdriver 2.0.3
File Interpreter ABI Platform
grsdriver-2.0.3-py3-none-any.whl Python 3 none any Details

Total release size: 3.4 MB

Release files / grsdriver-2.0.3.tar.gz

Download URL grsdriver-2.0.3.tar.gz
Size 1.7 MB
Tags Source
SHA-256 checksum
How to use checksums
8e1ee49d462aa266f8e94656289617056356125ddd06554e52e4ad7594189d4f
BLAKE2b-256 checksum
How to use checksums
fa3ba89efdb5229c452d4f430234a0d2981f220aa9c817edf2fe7cd0929acba2
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.14

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Oct 16, 2026.

Transparency log

Release files / grsdriver-2.0.3-py3-none-any.whl

Download URL grsdriver-2.0.3-py3-none-any.whl
Size 1.7 MB
Tags Python 3
SHA-256 checksum
How to use checksums
f7725fd04d424ece55323b1c521beba91ec8b9415ebbcf655b59f7d3f25e1a9d
BLAKE2b-256 checksum
How to use checksums
1692aa0f4ad7db84537b941ad389e0607accd82567ead92d39113abd4ad47b50
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.14

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Oct 16, 2026.

Transparency log

Release history Release notifications | RSS feed

This release

2.0.3 This release

2 release files

2.0.2

2 release files

2.0.1

2 release files

1.1.1

2 release files

1.1.0

2 release files

1.0.8

2 release files

1.0.7

2 release files

1.0.6

2 release files

1.0.5

2 release files

1.0.4

2 release files

1.0.3

2 release files

1.0.1

2 release files

1.0.0

2 release files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page