Library / SDK
pytroll/satpy avatar
pytroll/satpy

Satpy: turning satellite instrument data into images with xarray and Dask

Python package for earth-observing satellite data processing

1,212 stars336 forksPythonApache-2.0

At a glance

What is it?
Satpy is the PyTroll Python library for reading and manipulating meteorological remote sensing data and writing it to image and data formats, with RGB composite generation, resampling through pyresample, and per-instrument optional dependencies that pull in the right readers.
Who is it for?
Satpy fits a researcher or operational team that works with level 1 or 2 satellite data and wants one API across instruments, composites generated on demand, and lazy arrays that scale to a single scene without loading it into memory. It does not fit someone who needs one specific file format, since the readers are in optional dependencies, and the learning curve is the price of the instrument independence.
Can I use it commercially?
Yes. Apache-2.0 is a permissive licence: you can use, modify and sell software built on it, as long as you keep its copyright and licence notices.
Is it still maintained?
Yes. The repository last received commits 8 days ago.
What is it written in?
Mainly Python, according to GitHub's language statistics.

Answers come from the project's GitHub data, last synced on October 22, 2026, and from our analysis. They are not legal advice.

Editorial analysis

One library across many instruments

Satpy is a Python library for reading and manipulating meteorological remote sensing data and writing it to various image and data file formats. It comes with the ability to make various RGB composites directly from satellite instrument channel data or higher level processing output.

The scope is worth understanding precisely. Satpy is not a remote sensing platform and it does not download data. It is the layer that sits between a file on disk, or an array in memory, and an image you can look at or hand to a downstream model. The instrument-specific knowledge, the calibration, the resampling and the composite recipes are all in the library.

The dependency list in the project metadata shows the shape of the design, and it is a scientific Python stack rather than a generic one. `dask[array]` provides the lazy arrays, `xarray` provides the labelled dimensions, `pyresample` handles resampling data to different uniform areas or grids, `trollimage` handles the image formats, `trollsift` does the filename parsing, `pyorbital` does the orbital calculations, and `donfig` provides the configuration system. `pooch` is the data file fetcher, `pykdtree` and `pyproj` support the geospatial work, and `zarr` is there for chunked array storage.

Two version floors tell you where the project is now: `numpy>=2.0` and `requires-python >=3.12`. The package is Apache-2.0 licensed, and the copyright line in the README says 2009 Satpy developers, so this is a project with a long history rather than a new arrival.

The optional dependency groups are the actual interface

The most important thing in the metadata is not the required dependencies, it is the optional ones, because they are how you pick the readers you need.

Each group corresponds to a reader family. `modis_l1b` pulls in `pyhdf` and `python-geotiepoints`, `viirs_l1b` pulls in `netCDF4`, `viirs_sdr` and `viirs_compact` pull in `h5py`, `amsr2_l1b` pulls in `h5py`, `abi_l1b` pulls in `h5netcdf`, `goci2`, `acspo` and `clavrx` pull in `netCDF4`, and `acspo` and `clavrx` again. `sar_c` pulls in `python-geotiepoints`, `rasterio`, `rioxarray` and `defusedxml`, `generic_image` pulls in `rasterio` and `rioxarray`, and `msi_safe` pulls in `rioxarray`, `bottleneck`, `python-geotiepoints` and `defusedxml`.

What this shows is the dependency cost of instrument coverage. Reading a level 1b file means a specific HDF, netCDF or h5py binding, and Satpy will not carry all of them by default. The tradeoff is deliberate, and it is the right one: a user working with one instrument does not pay for the readers of twenty others, and the package does not have to reconcile five different ways of opening a netCDF file.

The `hrpt` and `hrit_msg` groups show the same pattern for direct satellite downlink formats, with `hrpt` pulling in `pyorbital`, `pygac` and `python-geotiepoints`, and `hrit_msg` pulling in `pytroll-schedule`.

The `defusedxml` appearance in several groups is also deliberate. It is a hardened XML parser, and it appears alongside the readers that parse format descriptions which may come from outside the project.

Installation and the two ways to get it

The README documents two installation routes, one from PyPI and one from conda-forge.

bash
pip install satpy
bash
conda install -c conda-forge satpy

The conda-forge route is worth a note for anyone working with this kind of data, because the scientific Python stack around Satpy, xarray, dask, pyresample and the various netCDF and HDF bindings, is exactly the kind of stack where conda's binary dependency solving earns its keep. The README also carries a conda-forge version badge, which suggests the project tracks that channel carefully.

The package publishes to PyPI and to conda-forge, and it is archived on Zenodo with a DOI, which is the standard practice for research software and means a specific version can be cited permanently. There is a CITATION file in the repository for the same reason, and the classifiers mark the package as Production/Stable and intended for Science/Research audiences.

What the README does not spell out is the extras syntax, so if you need a specific instrument reader you would install the base package plus the group for that instrument rather than expecting every reader to be present.

The documentation is at satpy.readthedocs.io, and the project also carries an `asv.conf.json` and a `benchmarks/` directory, which means the performance of the library is tracked over time rather than being a matter of impression.

Composites, resampling and why xarray is in the middle

The two capabilities the README leads with are composite generation and resampling, and both come from the same underlying design.

A composite is a false-colour image assembled from instrument channels, and Satpy makes RGB composites directly from satellite instrument channel data or from higher level processing output. That means the composite definitions, with their channel selection and stretch, live in the library rather than in a script someone wrote.

Resampling is handled by pyresample, which Satpy uses to resample data to different uniform areas or grids. This is the step that puts the data onto a common projection so that channels from different instruments, or from different overpasses, can be combined into a single image.

The reason xarray sits at the centre is that it gives the data labelled dimensions, so a channel is an array with named axes rather than a bare numpy array, and the composite and resampling machinery can address the data by name. The reason dask is there is that the arrays are lazy, so a scene can be described as a graph of operations and computed only when written, which is what makes it feasible to work with full resolution satellite swaths at all.

`pooch` is the data file fetcher, and `zarr` provides chunked, compressed on-disk arrays, so an intermediate product can be stored and reloaded without regenerating it.

`donfig` is the configuration layer. The configuration is YAML-based, given the `pyyaml>=5.1` dependency, and the way Satpy is normally driven is by naming a reader and a composite in a configuration file, then calling a Scene on it.

The licence exception and the project structure

One file in the repository is under a different licence, and the README is upfront about it.

The EPS format description at `satpy/etc/eps_avhrrl1b_6.5.xml` is an unmodified third-party file, copyright EUMETSAT, distributed under the terms of the GNU General Public License version 2 or later, and it keeps its own licence notice. Everything else is Apache-2.0. So a copy of the package contains one GPL component, and a team shipping Satpy in a product with a different licence needs to account for that file.

That file exists because the AVHRR level 1b data in EPS format is described by an external specification, and shipping the description is what lets Satpy read that format without asking the user to supply it.

The rest of the tree is a well-organised research project. There is a `satpy/` package, `doc/` for the documentation, `tests/` implied by the CI badge, `benchmarks/` for the performance tracking, `continuous_integration/` for the CI configuration, and `utils/`. The project metadata is in `pyproject.toml` with a dynamic version, and the release process has its own `RELEASING.md` and `CHANGELOG.md`.

The governance files are worth a look. There is a `CONTRIBUTING.rst`, a `CODE_OF_CONDUCT.md` that follows the PyTroll project code of conduct, an `AUTHORS.md`, a `SECURITY.md` for reporting vulnerabilities, and a `CITATION` file. The README names the core maintainers as David Hoese, Martin Raspaud and Adam Dybbroe, and describes the consequence of the code of conduct in practical terms, including the escalating sanctions from a verbal warning through a public apology to a temporary or permanent ban from events and from the Slack team, mailing list and Twitter account.

The last push was on 2026-10-14, and the newest release is v0.60.0 from 2026-03-04, after v0.59.0 in November 2025 and v0.58.0 in August 2025, so roughly quarterly releases with continuous work between them.

Editorial conclusion

Satpy fits a researcher or operational team that works with level 1 or 2 satellite data and wants one API across instruments, composites generated on demand, and lazy arrays that scale to a single scene without loading it into memory. It does not fit someone who needs one specific file format, since the readers are in optional dependencies, and the learning curve is the price of the instrument independence. Before installing, add the optional dependency group for your instrument, for example `pip install satpy[modis_l1b]`, and check the `satpy/etc/eps_avhrrl1b_6.5.xml` file's separate licence if you work with that AVHRR EPS description.

Frequently asked questions

What is Satpy?

It is a Python library for reading and manipulating meteorological remote sensing data and writing it to various image and data file formats, with the ability to make RGB composites directly from satellite instrument channel data. It is part of the PyTroll project and Apache-2.0 licensed.

How do I install Satpy?

With `pip install satpy` from PyPI, or `conda install -c conda-forge satpy` for conda installations. Python 3.12 or newer is required, along with numpy 2.0 or newer.

How do I enable support for a specific satellite instrument?

Through the optional dependency groups in the project metadata, each of which pulls in the readers that instrument needs. Examples include modis_l1b for pyhdf and python-geotiepoints, viirs_l1b for netCDF4, viirs_sdr for h5py, abi_l1b for h5netcdf, and sar_c for rasterio, rioxarray and defusedxml.

What does Satpy use pyresample for?

Resampling data to different uniform areas or grids, which is the step that puts channels onto a common projection so they can be combined into a single composite image. The resampling itself is done by the pyresample package.

Is any part of Satpy under a different licence?

Yes. The EPS format description at satpy/etc/eps_avhrrl1b_6.5.xml is an unmodified third-party file, copyright EUMETSAT, distributed under the GNU General Public License version 2 or later with its own notice. The rest of the project is Apache-2.0.

Official sources

  1. License: Apache-2.0
  2. Project website
  3. pytroll/satpy on GitHub
  4. README
  5. Releases
Add this badge to your README

If you maintain this project, the badge below links readers to this analysis and shows its maintenance status from the daily GitHub snapshot. Paste the markdown into your README; add ?metric=license or ?metric=stars to the image URL for a different field.

Add this badge to your README

markdown
[![Hysen Labs](https://hysenlabs.com/badge/pytroll-satpy.svg)](https://hysenlabs.com/projects/pytroll-satpy)