A Python benchmark accompanying A Benchmark of an Ethanol Steam Reformer for Clean Hydrogen Production, by Mateo Arcila-Osorio, Hernan Alvarez and Carlos Ocampo-Martinez.
The simulator models catalytic ethanol steam reforming followed by hydrogen separation in a staged-separation membrane reactor (SSMR). It provides open-loop and closed-loop simulations, measured outlet signals, internal state profiles, disturbances and performance metrics. It is simulation-only; no laboratory connection or proprietary software is required.
Use Python 3.12. From a terminal:
git clone https://github.com/arcmateo/ESR_Benchmark.git
cd ESR_Benchmark
python -m venv .venvActivate the environment:
# Windows PowerShell
.\.venv\Scripts\Activate.ps1# macOS / Linux
source .venv/bin/activateIf PowerShell prevents activation, use .\.venv\Scripts\python.exe in place of python below. If using the downloaded ZIP, extract it and open a terminal in the directory containing this README; skip git clone.
python -m pip install -r requirements.txt
python run_benchmark.py --config examples/nominal.jsonThe nominal example runs the chapter's 30-minute case at 773.15 K, 4 bar, 0.0021 mol/min ethanol and 0.0099 mol/min water, with 50 partitions per stage and SciPy's BDF solver. The supplied initial state is already near nominal steady state. Expect a final total hydrogen permeate flow close to 0.000246470 mol/min. This is a model regression reference, not new experimental validation.
Open results/nominal/axial_profiles.png for the composition-flow and temperature profiles corresponding to the conditions of chapter Figure 2. timeseries.png shows the outlet measurements and feed inputs.
python run_benchmark.py --config examples/tracking.json
python run_benchmark.py --config examples/temperature_step.json
python run_benchmark.py --config examples/pressure_step.json
python run_benchmark.py --config examples/deactivation.json
python run_benchmark.py --config examples/fouling.json| Example | Purpose |
|---|---|
nominal.json |
Open-loop chapter Figure 2 operating conditions, 30 min |
tracking.json |
Illustrative PID; reference changes at 2 and 4 min, 6 min total |
temperature_step.json |
D1: +10% inlet temperature step in kelvin at 1 min |
pressure_step.json |
D2: +20% inlet pressure step at 1 min |
deactivation.json |
D3: exponentially decreasing activity applied to all reactions |
fouling.json |
D4: exponentially decreasing membrane permeability |
D1-D4 run for 5 min in closed loop. Set mode to open_loop for uncontrolled comparisons. For negative steps, change relative_step to -0.10 or -0.20. D3/D4 use exp(-k*(t-start)) after onset, with illustrative k = 0.02 min^-1; these rates are configurable and are not calibrated or reported chapter results. The PID is a baseline demonstration, not an optimized controller; infeasible demands can lead to sustained error at the feed limits.
To reproduce the complete example set and matched comparisons:
python run_suite.pyThis also runs an open-loop tracking comparison and a nominal closed-loop run matched to the fouling case. results/suite/comparison.csv compares tracking, ethanol consumption and an explicitly normalized equal-weight cost. fouling_ratio.csv gives actual/nominal hydrogen flow under matched conditions. These support the first five challenges in chapter Table 3. Energy optimization (challenge 6) requires additional heater-power and pumping-work equations and is an extension, not an implemented calculation.
Copy an example JSON, edit it and pass its path with --config. Important settings are inputs, duration_min, sample_time_min, output_step_min, disturbance, setpoint, controller and solver. All flows are mol/min, time min, temperature K, and pressure Pa. Feed bounds are enforced for controllers: ethanol 0.0018-0.0024 and water 0.0087-0.0108 mol/min. Nominal inlet limits are 773.15-873.15 K and 1-14 bar; the specified disturbance is applied on top of nominal values. The chapter's negative 10% temperature test at 773.15 K therefore falls below its nominal temperature range.
Each run writes:
config.jsonandmetrics.json: exact settings, metrics and library versions;measurements.csv: aligned outlet signals, references and actual inputs;states.npz: all 900 states and control history on the saved time grid;axial_profiles.csv,axial_profiles.png,timeseries.png: reusable data and plots.
Existing result folders are protected. To rerun, choose a new destination:
python run_benchmark.py --config examples/nominal.json --output results/nominal_repeatPermeate volume is reported for pure hydrogen at 298.15 K and 101325 Pa; retentate volume uses instantaneous outlet temperature and pressure. The controller uses total permeate molar flow, consistently derived from the same model. Saved measurements are calculated at accepted solution states, without filtering. See model and controller guide for state ordering, custom controllers and metric definitions.
run_benchmark.py / run_suite.py Single example / complete comparison suite
configuration.py / parameters.py Settings, physical parameters and initial state
model.py / runner.py Balance equations and BDF simulation
controller.py / scenarios.py Controller interface and disturbances
measurements.py / metrics.py Measured signals and performance measures
postprocess.py CSV, NPZ, JSON and figure export
examples/ Editable example configurations
data/ Supplied initial conditions
docs/ Usage guide, validation and supplementary PDF
tests/ Regression and workflow checks
python -m unittest discover -s tests -vThen run python run_suite.py --output results/verification for the complete workflow. See validation record for the tested environment and results. GitHub Actions runs the short test suite; local validation also covers all full-duration examples.
Use the repository folder as the working directory and the environment above as the interpreter. In Jupyter or Spyder:
from configuration import load_config
from runner import run
from postprocess import save
result = run(load_config("examples/nominal.json"))
summary = save(result, "results/notebook_nominal")In Colab, run !git clone https://github.com/arcmateo/ESR_Benchmark.git, then %cd ESR_Benchmark, %pip install -r requirements.txt and the Python example above. If the notebook has already imported a different NumPy/SciPy version, restart its kernel/runtime after installation and return to the repository folder. The pinned environment requires Python 3.12; check the hosted runtime before installing. Remote environments and the eventual GitHub publication are not part of local verification.
Please cite the chapter title and authors above when using the benchmark. Machine-readable metadata are provided in CITATION.cff; publication identifiers can be added when available. The supplementary material contains the model derivation and constitutive equations. The chapter PDF is not redistributed here.
Code is provided under the MIT license. The supplementary PDF is provided for scientific reference and retains its authors' rights; the code license does not relicense that document.
