Claims development and stochastic reserving: chain ladder, Bornhuetter-Ferguson, Mack, and the over-dispersed-Poisson bootstrap of the predictive reserve distribution.
Project description
reservingmodels
Claims development and stochastic reserve estimation, from the triangle to the predictive distribution.
Overview
reservingmodels is the single place to reach for claims-reserving work. The
deterministic engine — chain-ladder development, completion factors, the
Bornhuetter–Ferguson / Benktander / Cape Cod methods, and Mack's analytic
standard errors — is re-exported from actuarialpy, where those triangle
primitives already live because the projection and pricing packages build on
them. On top of them this package adds the stochastic layer: the
over-dispersed-Poisson bootstrap of England & Verrall, which produces the full
predictive distribution of the unpaid claims, plus residual diagnostics for
checking the model before you trust the numbers.
A fitted BootstrapODP exposes .sample(size, rng), so it plugs straight into
risksim as a portfolio component —
reserve risk aggregated with prospective underwriting risk, with no dependency
between the two packages.
Installation
pip install reservingmodels
Requires Python 3.10 or newer. Pulls in actuarialpy for the shared triangle
primitives.
Quick start
import reservingmodels as rv
triangle = rv.datasets.taylor_ashe() # a cumulative K x K triangle
# --- deterministic: the point estimate (re-exported chain ladder) ---------- #
cl = rv.ChainLadder.fit(triangle)
print(cl.project(triangle)) # per-origin ultimate and IBNR
print(cl.mack_standard_errors(triangle)) # Mack (1993) analytic SE
# --- stochastic: the predictive distribution ------------------------------- #
boot = rv.BootstrapODP.fit(triangle)
dist = boot.reserve_distribution(size=100_000, rng=42)
print(f"reserve (point) : {dist.point_reserve:,.0f}")
print(f"prediction error : {dist.prediction_error():,.0f}")
print(f"75th / 99th pct : {dist.quantile(0.75):,.0f} / {dist.quantile(0.99):,.0f}")
print(f"TVaR(99%) : {dist.tvar(0.99):,.0f}")
print(dist.to_frame().round(0)) # per-origin + total exhibit
# --- reserve risk as a capital component ----------------------------------- #
import risksim as rs
port = rs.Portfolio([rs.PortfolioItem("reserve_risk", boot)]) # .sample seam
sim = port.simulate(100_000, rng=7)
print(f"portfolio TVaR : {rs.metrics.tvar(sim.gross_losses, 0.99):,.0f}")
What's inside
- Triangles and deterministic methods — re-exported from
actuarialpy:ChainLadder,completion_factors,apply_completion,develop_ultimate(chain-ladder, Bornhuetter–Ferguson, Benktander, Cape Cod),make_completion_triangle, and Mack'smack_standard_errors. These are aliases, not copies —rv.ChainLadder is actuarialpy.ChainLadder. - Stochastic reserving —
BootstrapODP, the semiparametric ODP bootstrap (estimation error by residual resampling, process error by a gamma draw), andReserveDistributionfor percentiles, VaR, TVaR, and a per-origin exhibit. - Diagnostics —
pearson_residuals,residual_summary, andcalendar_year_effectsfor checking the ODP assumptions. - The
risksimseam —BootstrapODP.sample(size, rng)makes the reserve a portfolio component;risksimaggregates it with other risks. - The Experience seam —
reservingmodels.integrations.actuarialpybuilds a triangle (and a fitted bootstrap) from a claims-listingactuarialpy.Experience.
The full API reference and worked examples live at openactuarial.org/reservingmodels.html.
The OpenActuarial ecosystem
reservingmodels shares the ecosystem conventions — tidy tables, explicit
parameterizations, reproducible random-number handling — and composes across
package seams:
| Package | Role |
|---|---|
| actuarialpy | Calculation primitives the workflow packages build on (incl. triangle mechanics and Mack) |
| experiencestudies | Experience reporting, actual-vs-expected, claimant and concentration analysis |
| projectionmodels | Claim, premium, and expense projection over a renewal horizon |
| ratingmodels | Manual and experience rating, credibility, indication, GLM relativities |
| reservingmodels | Claims development and stochastic reserving: chain ladder, BF, Mack, ODP bootstrap |
| lossmodels | Severity and frequency fitting, aggregate loss distributions |
| extremeloss | Extreme-value tails: POT/GPD, GEV, return levels, splicing |
| risksim | Portfolio Monte Carlo, dependence, reinsurance contracts, risk measures |
Install everything at once with pip install openactuarial.
Development
git clone https://github.com/OpenActuarial/reservingmodels
cd reservingmodels
python -m pip install -e ".[dev]"
pytest
ruff check src tests
CI runs the same gate on Python 3.10–3.14 across Linux and Windows.
Versioning and stability
All ecosystem packages are pre-1.0: minor releases may change APIs, and every release is documented in CHANGELOG.md. Current per-package API stability is tracked at openactuarial.org/stability.html.
License
MIT — see LICENSE.
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file reservingmodels-0.1.0.tar.gz.
File metadata
- Download URL: reservingmodels-0.1.0.tar.gz
- Upload date:
- Size: 22.7 kB
- Tags: Source
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
159082f21a0b7e962d877ae5293bb812babd3bf279039659db155c09a5e74147
|
|
| MD5 |
68785716dab390843c07d64d3ee03a34
|
|
| BLAKE2b-256 |
33cb1b947449d4ab853b0b7791121b28344c3c7aec292e8a5ba89aa3d6f4c0d2
|
Provenance
The following attestation bundles were made for reservingmodels-0.1.0.tar.gz:
Publisher:
release.yml on OpenActuarial/reservingmodels
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
reservingmodels-0.1.0.tar.gz -
Subject digest:
159082f21a0b7e962d877ae5293bb812babd3bf279039659db155c09a5e74147 - Sigstore transparency entry: 2169284443
- Sigstore integration time:
-
Permalink:
OpenActuarial/reservingmodels@1f9ed66927dbca25c48f76a11d999bcbf3697c8b -
Branch / Tag:
refs/tags/v0.1.0 - Owner: https://github.com/OpenActuarial
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
release.yml@1f9ed66927dbca25c48f76a11d999bcbf3697c8b -
Trigger Event:
push
-
Statement type:
File details
Details for the file reservingmodels-0.1.0-py3-none-any.whl.
File metadata
- Download URL: reservingmodels-0.1.0-py3-none-any.whl
- Upload date:
- Size: 17.3 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
63221b45bb7d961e207045ade48baa4335dfcf02078b40fdd61cd0786e18ea22
|
|
| MD5 |
c670ffb9d0d433fccbecc279fabed8bc
|
|
| BLAKE2b-256 |
f96e7375fcf9ccbc7d0d9d62bac5f1308fd24ddcd6eb2d201887d7b5ab4aa73e
|
Provenance
The following attestation bundles were made for reservingmodels-0.1.0-py3-none-any.whl:
Publisher:
release.yml on OpenActuarial/reservingmodels
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
reservingmodels-0.1.0-py3-none-any.whl -
Subject digest:
63221b45bb7d961e207045ade48baa4335dfcf02078b40fdd61cd0786e18ea22 - Sigstore transparency entry: 2169284471
- Sigstore integration time:
-
Permalink:
OpenActuarial/reservingmodels@1f9ed66927dbca25c48f76a11d999bcbf3697c8b -
Branch / Tag:
refs/tags/v0.1.0 - Owner: https://github.com/OpenActuarial
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
release.yml@1f9ed66927dbca25c48f76a11d999bcbf3697c8b -
Trigger Event:
push
-
Statement type: