chemthermo
Phase equilibrium for chemical engineering in Python: tangent-plane stability, multiphase TP flash, Peng-Robinson, PC-SAFT (with association and polymers) and NRTL, in SI units, with every numerical claim traceable to a recorded cross-check.
Status: beta (0.4.0). The science is checked against independent implementations, but the public API may still change before 1.0. Python
= 3.11; tested on macOS arm64 and Linux x86_64. MIT licence.
Install
pip install chemthermo
or pin a tagged commit from GitHub:
pip install "chemthermo @ git+https://github.com/AhmadAlkadri/Chemical-Thermodynamics.git@v0.4.0"
Runtime dependencies: numpy, pydantic, bibtexparser (< 2).
Quick start
A flash that decides for itself how many phases there are:
import chemthermo as ct
mixture = ct.Mixture.from_database(["Methane", "Ethane", "Propane"], [0.5, 0.3, 0.2])
result = ct.flash_tp(mixture, temperature_K=240.0, pressure_Pa=3.0e6, eos=ct.PengRobinsonEOS())
print(result.phase_names()) # ['liquid', 'vapor']
print(result.vapor_fraction) # 0.468...
print(result.phases["vapor"].composition.fractions)
Stability of a feed, and the phase it would split off:
check = ct.stability_tp(
ct.Mixture.from_database(["Methane", "n-Hexane"], [0.5, 0.5]),
temperature_K=300.0, pressure_Pa=2.0e6, eos=ct.PengRobinsonEOS(),
)
print(check.status, check.tpd_min) # unstable -1.2558...
print(check.phase_branch, check.trial_composition)
Three liquids, PC-SAFT, and residual properties:
from chemthermo.eos import PCSAFTEOS
three = ct.flash_tp(
ct.Mixture.from_database(["Water", "Ethanol", "n-Hexane"], [0.2, 0.4, 0.4]),
temperature_K=280.0, pressure_Pa=101325.0, eos=ct.PengRobinsonEOS(),
)
print(three.phase_names()) # ['liquid1', 'liquid2', 'liquid3']
water = PCSAFTEOS(components=("Water",))
rho = max(water.density_roots(temperature_K=300.0, pressure_Pa=1.0e5, composition=[1.0]))
props = water.residual_properties(temperature_K=300.0, density_mol_m3=rho, composition=[1.0])
print(props["h_res"], props["s_res_tp"]) # H^res/RT and S^res/R (ideal gas at same T, P)
From the command line:
chemthermo tp-flash --components Methane,Ethane,Propane --z 0.5,0.3,0.2 \
--temperature-k 240 --pressure-pa 3e6 --format json
chemthermo stability-tp --components Methane,n-Hexane --z 0.5,0.5 \
--temperature-k 300 --pressure-pa 2e6 --eos pc-saft
What it does
| Capability | Models | Checked against (ledger case) |
|---|---|---|
Tangent-plane stability, incipient-phase composition (stability_tp) |
Peng-Robinson, PC-SAFT, NRTL (liquid-liquid), NRTL + ideal gas | thermo 0.6 Michelsen test, same verdicts (S-4); Tessier et al. (2000) published global minima to 2e-11 (S-6, S-7); teqp (P-4) |
TP flash with automatic phase count, 1-3 phases (flash_tp) |
Peng-Robinson and PC-SAFT (phi-phi), NRTL (gamma-gamma), NRTL + Raoult (modified-raoult) |
thermo FlashVL (F-1); teqp's traced PC-SAFT isotherm, tie lines to 2e-9 (P-5); FeOs flash and chemical potentials (P-7, P-8); a published multiphase Rachford-Rice table (V-4); a ternary VLLE tie triangle (V-1) |
Peng-Robinson with per-pair kij |
cubic EOS | thermo PRMIX (K-1); agreement floored at ~1e-4 in ln phi by chemthermo's rounded constants (S-4) |
PC-SAFT residual Helmholtz, Z, ln phi, density roots |
Gross & Sadowski 2001 | teqp, better than 3e-14 (P-1, P-3) |
| PC-SAFT association (2B scheme) | Gross & Sadowski 2002 | FeOs, association term to 3e-15 (P-6) |
| PC-SAFT polymers (segments per mass, long chains in log space) | monodisperse chains | FeOs, 5e-12 with matched constants (P-12 - P-14) |
PC-SAFT residual H, S, U, G and d(A^res/RT)/dT |
incl. association | teqp Ar10 to 5e-16 (P-19); FeOs residual entropy/enthalpy to 2e-15 (P-20) |
| NRTL activity coefficients | NRTL | thermo NRTL to 9e-16 (N-2) |
Command line: tp-flash, stability-tp |
PR, PC-SAFT | golden JSON fixtures; exit-code contract |
Packaged data: critical constants, acentric factors and Antoine coefficients for 82 components (from Koretsky, Engineering and Chemical Thermodynamics); PC-SAFT parameters for 16 (11 non-associating, plus water, methanol, ethanol, 1-propanol and n-butanol with 2B association).
What "checked" means here. The comparisons above are code against
independent implementations (teqp, FeOs, thermo) or published worked
problems. They show the equations are implemented correctly. They say nothing
about how well a model with these parameters matches experiment, and nothing
in this repository claims that.
Limits, stated plainly
- "Stable" is not a proof. It means no negative tangent-plane distance was found from a deterministic set of trial compositions. A phase that no trial reaches can be missed, and a flash's phase count inherits that limit.
- Bring your own interaction parameters. No binary
kijtable ships. The two packaged NRTL pairs are synthetic placeholders for demos: real NRTL work needs your own parameters (NRTLParameters.from_pairs). PC-SAFT withkij = 0gets water / hydrocarbon mutual solubilities badly wrong. - Residual properties only. No ideal-gas heat capacities are packaged, so
no total enthalpy, entropy or
Cp; noCp^resyet. - PC-SAFT scope: no polar terms; only the 2B association scheme is validated; no induced association; polymers are monodisperse; no polymer parameters are packaged.
- Modified Raoult is a low-pressure model (ideal vapour, no Poynting correction); Antoine ranges are enforced, never extrapolated.
- Cost: a Peng-Robinson or activity-model flash takes milliseconds; PC-SAFT flashes take up to a few seconds (polymer and associating states the longest), and a three-phase PC-SAFT flash about 35 s.
- Deprecated:
flash_mode="gamma-phi"(kept for the CLI v1 contract; emitsDeprecationWarning).chemthermo.vllewas removed in 0.4.0.
Longer, model-specific limits are in the docs below.
Documentation
- Installation and development setup
- TP flash - phase detection, flash modes, three phases,
kij, NRTL - Phase stability
- PC-SAFT - parameters, association, polymers, residual properties, limits and their validation
- Command line
- Extending with a new equation of state
- Benchmarks and the robustness map
- Runnable scripts:
examples/; notebooks:notebooks/ - Changelog
How it is validated and developed
Every number quoted above has an entry in the validation ledger,
.agents/brain/validation-cases.md, with
its source, tolerance, achieved value and test. Design decisions are
recorded as ADRs in .agents/brain/adr/. The tests that
compare against teqp, FeOs and thermo run with pip install -e ".[validation]" and skip cleanly otherwise. A 2505-state robustness map
(python -m chemthermo.bench robustness) sweeps every model family; its only
refusals are 5 states of the deprecated gamma-phi path.
Contributions: see CONTRIBUTING.md.
Licence
MIT - see LICENSE.
Release files for chemthermo 0.4.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | |
|---|---|---|---|
| chemthermo-0.4.0.tar.gz | 244.3 kB | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| chemthermo-0.4.0-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 512.9 kB
Release files / chemthermo-0.4.0.tar.gz
| Download URL | chemthermo-0.4.0.tar.gz |
|---|---|
| Size | 244.3 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
d301b30c0a3dacf2e022dd1e144235fccfdea69d18cea0cca00f65322e203b0f
|
|
BLAKE2b-256 checksum How to use checksums |
14a8a8f8ed6db9e090b012339075cee8dad1f95294f6fc03a4af62d29138b65a
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/7.0.0 CPython/3.11.6
|
Release files / chemthermo-0.4.0-py3-none-any.whl
| Download URL | chemthermo-0.4.0-py3-none-any.whl |
|---|---|
| Size | 268.6 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
09e26d38cf9802d0c51e7814241d73bf7e0388c085e0efc62ca5b65fc3940fd2
|
|
BLAKE2b-256 checksum How to use checksums |
42f5fbd385147f361e86d91e2f892fd73015f6ec93864401ba7fc74ac76a47e9
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/7.0.0 CPython/3.11.6
|