Skip to main content

aquaswmm

A free, open-source (GPL) Python library for EPA SWMM models and storm sewer hydraulics: edit .inp files by table and column, run the EPA engine, read .rpt/.out results, and size pipes with the Rational method, Manning, standard-step HGL/EGL backwater and HEC-22 inlets. A native extension built from Rust, with no Python dependencies and no server.

The library is free to use for any purpose. It shares its readers and engine with the AquaSWMM desktop app, a separate paid product (aquaswmm.com). Nothing here needs the app or a license.

pip install aquaswmm

SWMM models: edit, run, read results

The same readers the AquaSWMM desktop app uses, so a script and the app agree on column names, run validity, and every number read back.

import aquaswmm as aq
import pandas as pd

m = aq.Model.open("site.inp")
pd.DataFrame(m.table("CONDUITS"))          # every row, by column name
m.get("CONDUITS", "C1", "Roughness")       # '0.013'
m.set("CONDUITS", "C1", "Roughness", 0.015)
m.set_option("ROUTING_STEP", "0:00:05")
m.rename("node", "J1", "MH-101")           # and every reference to it
m.validate()                               # the app's model checks

run = m.run("site_n015.inp")               # saves, then runs EPA SWMM
if not run.ok:
    print(run.problem)                     # failed, or blew up (NOT VALID)
run.continuity                             # {'Flow Routing Continuity': 0.015, ...}

res = run.results()                        # or aq.Results("site.out")
pd.DataFrame(res.node_peaks())             # max depth, inflow, flooding
res.link_series("C1", "flow")              # {'time_s': [...], 'value': [...]}
pd.DataFrame(res.froude())                 # Froude at peak flow and max

rep = run.report()                         # or aq.Report("site.rpt")
pd.DataFrame(rep.table("Node Depth Summary"))

Model values are strings, exactly as written in the file: a model keeps every line you did not edit byte for byte, comments and spacing included. aq.engines() lists the EPA SWMM engines found on the machine (set AQUASWMM_SWMM_ENGINE_DIR to add one); run(..., engine=<id>) picks one by the id it lists. A run that fails is returned, not raised — check run.ok.

Inside the desktop app, Tools → Python Terminal binds the current run as m, res and report when this package is installed in that Python.

Site flood forecasts

aquaswmm.forecast keeps a SWMM model running continuously so it carries antecedent conditions (soil moisture, water table, pond levels) from one day to the next, forces it with NOAA MRMS radar rain and HRRR / GEFS forecast rain, corrects it with USGS observations through an ensemble Kalman filter, and reports the probability of exceeding site thresholds.

pip install "aquaswmm[forecast]"     # numpy + eccodes for GRIB2
from aquaswmm.forecast import read_hotstart, spinup, advance

h = read_hotstart("end.hsf", "site.inp")   # SWMM 5.2 hotstart, read against its model
h.variables("groundwater", "S1")           # theta, water_table, flow, max_infil_vol
h.set("node", "Pond", "depth", 3.0, model_units=True)
h.write("edited.hsf")                      # unedited files round-trip byte for byte

s = spinup("site.inp", start, end, rain, runs_dir="runs")   # cold start -> hotstart
s = advance(s, datetime.timedelta(hours=6), rain, runs_dir="runs")

The scheduled job is driven by one TOML site file:

python -m aquaswmm.forecast example > site.toml
python -m aquaswmm.forecast spinup site.toml     # chain observed rain from [spinup] start
python -m aquaswmm.forecast run site.toml        # advance, assimilate, forecast
python -m aquaswmm.forecast hindcast site.toml   # replay past dates, Brier scores

run writes forecast.json, forecast.csv and forecast.html with each threshold's probability of exceedance and first-exceedance times. Hotstart files, continuous runs and the products need only the standard library; GRIB2 decoding and the filter need the forecast extra. The full description, data sources and limits are in the Site forecasts chapter of the manual.

Storm sewer primitives

Float in, float out. Useful for replacing a spreadsheet column.

import aquaswmm as ss

ss.intensity(60, 10, 0.8, 12)          # IDF: i = a/(t+b)^c  ->  5.0607 in/hr
ss.rational_q(0.70, 5.0607, 1.0)       # Q = C i A           ->  3.5425 cfs
ss.manning_capacity(1.25, 0.013, 0.005)  # just-full capacity ->  4.5801 cfs
ss.normal_depth(3.5425, 1.25, 0.013, 0.005)  # -> 0.8254 ft (None if it won't fit)
ss.critical_depth(3.5425, 1.25)
ss.circular_geometry(1.25, 0.8254)
# {'area': 0.8597, 'wetted_perimeter': ..., 'hydraulic_radius': ..., 'top_width': ...}

Pass si=True for metric: the Manning factor becomes 1.0 and g becomes 9.81.

ss.manning_capacity(0.4, 0.013, 0.005, si=True)   # m3/s

Whole networks

import aquaswmm as ss
import pandas as pd

result = ss.analyze_project(ss.demo_project_json())

pipes = pd.DataFrame(result["pipes"])
print(pipes[["id", "design_q", "capacity", "pct_full", "velocity", "hgl_up"]])

nodes = pd.DataFrame(result["nodes"])
print(nodes[nodes.floods])          # anything surcharging to the surface

analyze_file("project.ssproj") reads a file saved by the desktop app, and analyze_ssn(text) takes the plain-text network format:

ss.analyze_ssn("""
IDF        60 10 0.8
TAILWATER  100.5
MINTC      10

NODE N1   inlet    0    0  104.0  110.0  1.0  0.70  12
NODE OUT  outfall  300  0  102.5  108.5

PIPE P1   N1  OUT  300  1.25  0.013
""")

Each pipe dict carries id, from, to, slope, total_ca, tc, travel_time, intensity, design_q, capacity, pct_full, velocity, normal_depth, critical_depth, hgl_up, hgl_dn, and surcharged. Each node dict carries id, tc, rim, hgl, freeboard, and floods.

Constants

K_MANNING_US (1.486), K_MANNING_SI (1.0), G_US (32.2), G_SI (9.81).

The engine uses K = 1.486, the exact unit conversion, matching Autodesk Hydraflow and HEC-22 rather than the rounded 1.49 some spreadsheets use, a 0.27% difference in capacity. The validation page works every number on a reference network by hand.

What this is not

It computes the published equations; it does not decide whether the Rational method suits your site, what C to use, or which storm to design for. Those stay with the engineer sealing the drawing.

License

GPL-3.0-or-later, like the AquaSWMM engine.

Metadata

Release files for aquaswmm 0.12.4

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

Source distribution (sdist)

Source distribution for aquaswmm 0.12.4
File Size Uploaded Provenance
aquaswmm-0.12.4.tar.gz 2.8 MB With provenance Details

Built distributions (wheels)

Table of built distributions (wheels) for aquaswmm 0.12.4
File Interpreter ABI Platform
aquaswmm-0.12.4-cp39-abi3-win_amd64.whl CPython 3.9 abi3 Windows x86-64 Details
aquaswmm-0.12.4-cp39-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl CPython 3.9 abi3 Linux glibc 2.17+ x86-64 Details
aquaswmm-0.12.4-cp39-abi3-macosx_10_12_x86_64.macosx_11_0_arm64.macosx_10_12_universal2.whl CPython 3.9 abi3 macOS 10.12+ universal2 (ARM64, x86-64), macOS 11.0+ ARM64, macOS 10.12+ x86-64 Details

Total release size: 7.4 MB

Release files / aquaswmm-0.12.4.tar.gz

Download URL aquaswmm-0.12.4.tar.gz
Size 2.8 MB
Tags Source
SHA-256 checksum
How to use checksums
a3310d2058872f64d0ab5d4a9d041793caf73ae7ab28aa11531da179ac772874
BLAKE2b-256 checksum
How to use checksums
210b87b21ba0952fbed754525a4dca858ee81b92b28f218ea323740833765944
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 6, 2026.

Transparency log

Release files / aquaswmm-0.12.4-cp39-abi3-win_amd64.whl

Download URL aquaswmm-0.12.4-cp39-abi3-win_amd64.whl
Size 1.8 MB
Tags CPython 3.9 Windows x86-64 abi3
SHA-256 checksum
How to use checksums
1b2a5b35499a6aec0e666b72cfd98015e13609b1be70a88bebbedace0ef95ee6
BLAKE2b-256 checksum
How to use checksums
90abbad07ec509aeba084c63514d81e89c96006df43d75b6521038c0dfc1fea1
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 6, 2026.

Transparency log

Release files / aquaswmm-0.12.4-cp39-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl

Download URL aquaswmm-0.12.4-cp39-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl
Size 1.1 MB
Tags CPython 3.9 Linux glibc 2.17+ x86-64 abi3
SHA-256 checksum
How to use checksums
8777e1db919c93c5a699a3d9c0e5d46428a10eea5eb7be646fdeb53ec4754a9f
BLAKE2b-256 checksum
How to use checksums
627e27e6a278d0d2c6232d06bf65a9af7ece7f663d4a3a8f5499d3b5ecfbaf44
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 6, 2026.

Transparency log

Release files / aquaswmm-0.12.4-cp39-abi3-macosx_10_12_x86_64.macosx_11_0_arm64.macosx_10_12_universal2.whl

Download URL aquaswmm-0.12.4-cp39-abi3-macosx_10_12_x86_64.macosx_11_0_arm64.macosx_10_12_universal2.whl
Size 1.7 MB
Tags CPython 3.9 abi3 macOS 10.12+ universal2 (ARM64, x86-64) macOS 10.12+ x86-64 macOS 11.0+ ARM64
SHA-256 checksum
How to use checksums
11bd2780d86096cc5d90713bfce742557a00273a9778df146c3284ab4e6840eb
BLAKE2b-256 checksum
How to use checksums
9433f206981fb6bb0eb316fe0e8175ed40f9f71bbe77e6fec1e9d34eac05ff1d
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 6, 2026.

Transparency log

Security for aquaswmm 0.12.4

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.

Full provenance

All 4 files in this release have been uploaded with provenance metadata.

Select from 4 files

Attestation for aquaswmm-0.12.4.tar.gz

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 6, 2026.

Transparency log

A note on package security

PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.

To learn more about protecting yourself from malicious actors, visit our package security documentation.

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