Precipitation Index
  • Home
  • Get Started
    • Installation
    • Quick Start
    • Configuration
    • Data Model & Outputs
    • Examples
  • Tutorials
    • Calculate SPI
    • Calculate SPEI
    • Event Analysis
    • Visualization Gallery
  • Documentation
    • User Guide
    • Technical Docs
  • Changelog

Precipitation Index

SPI & SPEI for Climate Extremes Monitoring

Monitor Climate Extremes with Confidence

A minimal, efficient Python implementation of Standardized Precipitation Index (SPI) and Standardized Precipitation Evapotranspiration Index (SPEI) for monitoring both drought and wet conditions using run theory.

Python 3.8+ BSD-3-Clause Active Development

Get Started View on GitHub


Key Features

Climate Indices

  • SPI — Standardized Precipitation Index
  • SPEI — Precipitation Evapotranspiration Index
  • Multiple time scales (1, 3, 6, 12, 24 months)
  • CF-compliant NetCDF output

Bidirectional Analysis

  • Monitor drought (dry conditions)
  • Monitor floods (wet conditions)
  • Unified framework for both extremes
  • Consistent methodology

Multi-Distribution Fitting

  • Gamma — Standard for SPI
  • Pearson III — Recommended for SPEI
  • Log-Logistic — Better tail behavior
  • Automatic fitting method selection

Run Theory Framework

  • Event identification & characterization
  • Duration, magnitude, intensity, peak
  • Time-series and gridded analysis
  • Period statistics for spatial patterns

Operational Mode

  • Save fitted distribution parameters
  • Load and apply to new data without refitting
  • Production monitoring workflows
  • Validated identical to fresh calculations

Scalable Processing

  • Memory-efficient spatial tiling
  • Process global-scale data (CHIRPS, ERA5)
  • Automatic memory estimation
  • Streaming I/O for large datasets

Quick Example

  • Basic Usage
  • Operational Mode
import xarray as xr
from indices import spi
from runtheory import identify_events
from visualization import plot_index

# Load precipitation data
precip = xr.open_dataset('precipitation.nc')['precip']

# Calculate SPI-12
spi_12 = spi(precip, scale=12)

# Or use different distributions
spi_12_p3 = spi(precip, scale=12, distribution='pearson3')

# Identify drought events using run theory
events = identify_events(spi_12.isel(lat=0, lon=0), threshold=-1.2)

# Visualize
plot_index(spi_12.isel(lat=0, lon=0), threshold=-1.2)
from indices import spi, save_fitting_params, load_fitting_params

# Step 1: Calibrate on historical data and get parameters
spi_hist, params = spi(precip_historical, scale=12, return_params=True)

# Step 2: Save parameters for future use
save_fitting_params(params, 'spi12_gamma_params.nc',
                    scale=12, periodicity='monthly',
                    distribution='gamma',
                    coords={'lat': precip.lat.values,
                            'lon': precip.lon.values})

# Step 3: Later — load params and apply to new data (no refitting)
loaded = load_fitting_params('spi12_gamma_params.nc',
                             scale=12, periodicity='monthly',
                             distribution='gamma')
spi_new = spi(precip_new, scale=12, fitting_params=loaded)

Why precip-index?

NoteProduction-Ready Monitoring

Calibrate distribution parameters on historical data, save them as NetCDF, and apply consistently to new observations — no refitting needed. This enables operational drought monitoring workflows where new satellite data is processed the moment it arrives, using the same statistical baseline every time. Validated to produce results identical to fresh calculations.

TipGlobal-Scale Performance

Benchmarked on a workstation with 128 GB RAM:

  • CHIRPS v3 SPI-12 (0.05°, 17.3M cells, 539 months, ~69 GB) — ~2h 47m with Gamma distribution, 12 spatial chunks
  • TerraClimate SPEI-12 (0.04°, 37.3M cells, 804 months, ~224 GB) — ~26h with Pearson III distribution, 32 spatial chunks

Regional subsets (country-level) complete in seconds to minutes. Memory-efficient spatial tiling means you don’t need a supercomputer. See Performance Benchmarks for detailed comparison.

ImportantBuilt on Standards

WMO 11-category drought/wet classification. CF-compliant NetCDF output. Run theory from peer-reviewed hydrology literature. Multiple PET methods (Thornthwaite, Hargreaves) with automatic fallback. Three distribution families each using their optimal fitting method (Method of Moments, MLE, L-moments).


Global Output

  • SPI 12-month from CHIRPS
  • SPEI 12-month from TerraClimate

SPI-12 computed from global CHIRPS v3 dataset (0.05°) — December 2025

SPI-12 (Gamma) calculated from CHIRPS v3 at 0.05° resolution.

SPEI-12 computed from global TerraClimate dataset (0.0417° ~ 4km) — December 2024

SPEI-12 (Pearson III) calculated from TerraClimate at 0.0417° ~ 4km resolution.


Validation Results

All distributions tested against TerraClimate Bali data (1958–2024). Cross-distribution correlation exceeds 0.98. The test suite generates 28 visualizations including advanced analytics and operational mode validation.

  • Multi-Scale SPI
  • Distribution Comparison
  • PET Methods
  • Seasonal Heatmap
  • Historical Events
  • Decadal Trends
  • Climate Stripes
  • Exceedance Probability
  • Operational Mode

SPI at 1-, 3-, 6-, 12-, and 24-month scales. Each captures different drought types: meteorological, agricultural, hydrological, and socioeconomic.

Three distributions produce consistent SPI-12 time series with correlation > 0.98 between all pairs.

PET method comparison: Thornthwaite vs Hargreaves vs TerraClimate (Penman-Monteith). Hargreaves correlates better with the reference (r=0.80 vs r=0.75).

Seasonal drought heatmap showing month-by-year patterns. Major droughts (1997, 2015, 2019) appear as vertical red bands.

Run theory analysis identifies and ranks historical drought/wet events by magnitude.

Long-term analysis showing drought frequency, mean index, and trends by decade.

Climate stripes visualization showing annual drought conditions from 1959-2024. Red = drought years, blue = wet years.

Risk assessment plot showing probability of exceeding drought thresholds with return period annotations.

Parameter persistence for real-time monitoring: calibrate once on historical data, apply consistently to new observations. Results are identical to fresh calculations.

See Validation & Test Results for detailed analysis.


Getting Started

Installation

Install dependencies and clone the repository.

Install Now

Quick Start

Calculate your first SPI/SPEI in minutes.

Quick Start

Tutorials

Learn through interactive examples with real data.

View Tutorials


Documentation

  • User Guide — SPI, SPEI, run theory, and visualization
  • Technical Docs — Methodology, implementation, API reference
  • Validation — Test results and comparison plots
  • Changelog — Version history

Credits

Benny Istanto, GOST/DEC Data Group, The World Bank

Developed to support operational hydrometeorological monitoring — enabling the World Bank to regularly assess extreme dry and wet periods across regions.

Built upon the foundation of climate-indices by James Adams, with substantial modifications for multi-distribution support, bidirectional event analysis, and scalable processing.


Citation

@software{precip_index_2026,
  author = {Istanto, Benny},
  title = {Precipitation Index: SPI & SPEI for Climate Extremes Monitoring},
  year = {2026},
  url = {https://github.com/bennyistanto/precip-index},
  version = {2026.1}
}

Contributing & License

We welcome contributions! See our GitHub repository for bug reports, feature requests, and pull requests. Licensed under BSD-3-Clause.

WarningActive Development

This package is under active development. APIs may change. Please report issues on GitHub.

Back to top
Source Code
---
title: "Precipitation Index"
subtitle: "SPI & SPEI for Climate Extremes Monitoring"
toc: false
page-layout: full
---

::: {.hero-banner}
::: {.hero-logo}
![](images/logo-white-transparent.png)
:::

::: {.hero-content}
# Monitor Climate Extremes with Confidence

A minimal, efficient Python implementation of **Standardized Precipitation Index (SPI)** and **Standardized Precipitation Evapotranspiration Index (SPEI)** for monitoring **both drought and wet conditions** using run theory.

<span class="badge-custom badge-python">Python 3.8+</span>
<span class="badge-custom badge-license">BSD-3-Clause</span>
<span class="badge-custom badge-status">Active Development</span>

[Get Started](get-started/installation.qmd){.btn .btn-primary .btn-lg role="button"}
[View on GitHub](https://github.com/bennyistanto/precip-index){.btn .btn-outline-light .btn-lg role="button"}
:::
:::

---

## Key Features

::: {.grid-container}
::: {.feature-card}
### Climate Indices

- **SPI** — Standardized Precipitation Index
- **SPEI** — Precipitation Evapotranspiration Index
- Multiple time scales (1, 3, 6, 12, 24 months)
- CF-compliant NetCDF output
:::

::: {.feature-card}
### Bidirectional Analysis

- Monitor **drought** (dry conditions)
- Monitor **floods** (wet conditions)
- Unified framework for both extremes
- Consistent methodology
:::

::: {.feature-card}
### Multi-Distribution Fitting

- **Gamma** — Standard for SPI
- **Pearson III** — Recommended for SPEI
- **Log-Logistic** — Better tail behavior
- Automatic fitting method selection
:::

::: {.feature-card}
### Run Theory Framework

- Event identification & characterization
- Duration, magnitude, intensity, peak
- Time-series and gridded analysis
- Period statistics for spatial patterns
:::

::: {.feature-card}
### Operational Mode

- **Save** fitted distribution parameters
- **Load** and apply to new data without refitting
- Production monitoring workflows
- Validated identical to fresh calculations
:::

::: {.feature-card}
### Scalable Processing

- Memory-efficient spatial tiling
- Process global-scale data (CHIRPS, ERA5)
- Automatic memory estimation
- Streaming I/O for large datasets
:::
:::

---

## Quick Example

::: {.panel-tabset}
### Basic Usage

```python
import xarray as xr
from indices import spi
from runtheory import identify_events
from visualization import plot_index

# Load precipitation data
precip = xr.open_dataset('precipitation.nc')['precip']

# Calculate SPI-12
spi_12 = spi(precip, scale=12)

# Or use different distributions
spi_12_p3 = spi(precip, scale=12, distribution='pearson3')

# Identify drought events using run theory
events = identify_events(spi_12.isel(lat=0, lon=0), threshold=-1.2)

# Visualize
plot_index(spi_12.isel(lat=0, lon=0), threshold=-1.2)
```

### Operational Mode

```python
from indices import spi, save_fitting_params, load_fitting_params

# Step 1: Calibrate on historical data and get parameters
spi_hist, params = spi(precip_historical, scale=12, return_params=True)

# Step 2: Save parameters for future use
save_fitting_params(params, 'spi12_gamma_params.nc',
                    scale=12, periodicity='monthly',
                    distribution='gamma',
                    coords={'lat': precip.lat.values,
                            'lon': precip.lon.values})

# Step 3: Later — load params and apply to new data (no refitting)
loaded = load_fitting_params('spi12_gamma_params.nc',
                             scale=12, periodicity='monthly',
                             distribution='gamma')
spi_new = spi(precip_new, scale=12, fitting_params=loaded)
```
:::

---

## Why precip-index?

::: {.callout-note}
## Production-Ready Monitoring

Calibrate distribution parameters on historical data, save them as NetCDF, and apply consistently to new observations — **no refitting needed**. This enables operational drought monitoring workflows where new satellite data is processed the moment it arrives, using the same statistical baseline every time. Validated to produce results identical to fresh calculations.
:::

::: {.callout-tip}
## Global-Scale Performance

Benchmarked on a workstation with 128 GB RAM:

- **CHIRPS v3 SPI-12** (0.05°, 17.3M cells, 539 months, ~69 GB) — **~2h 47m** with Gamma distribution, 12 spatial chunks
- **TerraClimate SPEI-12** (0.04°, 37.3M cells, 804 months, ~224 GB) — **~26h** with Pearson III distribution, 32 spatial chunks

Regional subsets (country-level) complete in seconds to minutes. Memory-efficient spatial tiling means you don't need a supercomputer. See [Performance Benchmarks](technical/implementation.qmd#performance-benchmarks) for detailed comparison.
:::

::: {.callout-important}
## Built on Standards

WMO 11-category drought/wet classification. CF-compliant NetCDF output. Run theory from peer-reviewed hydrology literature. Multiple PET methods (Thornthwaite, Hargreaves) with automatic fallback. Three distribution families each using their optimal fitting method (Method of Moments, MLE, L-moments).
:::

---

## Global Output

::: {.panel-tabset}
### SPI 12-month from CHIRPS

![SPI-12 computed from global CHIRPS v3 dataset (0.05°) — December 2025](images/global-spi12-202512.png)

SPI-12 (Gamma) calculated from **CHIRPS v3** at 0.05° resolution.

### SPEI 12-month from TerraClimate

![SPEI-12 computed from global TerraClimate dataset (0.0417° ~ 4km) — December 2024](images/global-spei12-202412.png)

SPEI-12 (Pearson III) calculated from **TerraClimate** at 0.0417° ~ 4km resolution.
:::

---

## Validation Results

All distributions tested against TerraClimate Bali data (1958–2024). Cross-distribution correlation exceeds 0.98. The test suite generates **28 visualizations** including advanced analytics and operational mode validation.

::: {.panel-tabset}
### Multi-Scale SPI

![](images/spi_multiscale_comparison.png)

SPI at 1-, 3-, 6-, 12-, and 24-month scales. Each captures different drought types: meteorological, agricultural, hydrological, and socioeconomic.

### Distribution Comparison

![](images/spi_distribution_comparison.png)

Three distributions produce consistent SPI-12 time series with correlation > 0.98 between all pairs.

### PET Methods

![](images/pet_comparison_timeseries_scatter.png)

PET method comparison: Thornthwaite vs Hargreaves vs TerraClimate (Penman-Monteith). Hargreaves correlates better with the reference (r=0.80 vs r=0.75).

### Seasonal Heatmap

![](images/spi_12_seasonal_heatmap.png)

Seasonal drought heatmap showing month-by-year patterns. Major droughts (1997, 2015, 2019) appear as vertical red bands.

### Historical Events

![](images/spi_12_historical_events.png)

Run theory analysis identifies and ranks historical drought/wet events by magnitude.

### Decadal Trends

![](images/spi_12_decadal_trends.png)

Long-term analysis showing drought frequency, mean index, and trends by decade.

### Climate Stripes

![](images/spi_12_climate_stripes.png)

Climate stripes visualization showing annual drought conditions from 1959-2024. Red = drought years, blue = wet years.

### Exceedance Probability

![](images/exceedance_probability.png)

Risk assessment plot showing probability of exceeding drought thresholds with return period annotations.

### Operational Mode

![](images/operational_mode_workflow.png)

Parameter persistence for real-time monitoring: calibrate once on historical data, apply consistently to new observations. Results are identical to fresh calculations.
:::

See [Validation & Test Results](technical/validation.qmd) for detailed analysis.

---

## Getting Started

::: {.grid-container}
::: {.feature-card}
### Installation

Install dependencies and clone the repository.

[Install Now](get-started/installation.qmd){.btn .btn-primary}
:::

::: {.feature-card}
### Quick Start

Calculate your first SPI/SPEI in minutes.

[Quick Start](get-started/quick-start.qmd){.btn .btn-primary}
:::

::: {.feature-card}
### Tutorials

Learn through interactive examples with real data.

[View Tutorials](tutorials/01-calculate-spi.qmd){.btn .btn-primary}
:::
:::

---

## Documentation

- **[User Guide](user-guide/index.qmd)** — SPI, SPEI, run theory, and visualization
- **[Technical Docs](technical/index.qmd)** — Methodology, implementation, API reference
- **[Validation](technical/validation.qmd)** — Test results and comparison plots
- **[Changelog](changelog.qmd)** — Version history

---

## Credits

::: {.credits-section}
**Benny Istanto**, GOST/DEC Data Group, The World Bank

Developed to support operational hydrometeorological monitoring — enabling the World Bank to regularly assess extreme dry and wet periods across regions.

Built upon the foundation of [climate-indices](https://github.com/monocongo/climate_indices) by James Adams, with substantial modifications for multi-distribution support, bidirectional event analysis, and scalable processing.
:::

---

## Citation

```bibtex
@software{precip_index_2026,
  author = {Istanto, Benny},
  title = {Precipitation Index: SPI & SPEI for Climate Extremes Monitoring},
  year = {2026},
  url = {https://github.com/bennyistanto/precip-index},
  version = {2026.1}
}
```

---

## Contributing & License

We welcome contributions! See our [GitHub repository](https://github.com/bennyistanto/precip-index) for bug reports, feature requests, and pull requests. Licensed under [BSD-3-Clause](https://github.com/bennyistanto/precip-index/blob/main/LICENSE).

::: {.callout-warning}
## Active Development

This package is under active development. APIs may change. Please report issues on [GitHub](https://github.com/bennyistanto/precip-index/issues).
:::

© 2026 Benny Istanto. Licensed under BSD-3-Clause

Built with Quarto

  • View source
  • Report an issue