Check an .rpf file against the locked Raptrix Power Interchange contract, and see what the file contains.
Two questions:
- Does this file conform to schema v0.14.5?
- What is in it, including a stored solved power flow when the file carries one?
The package is standalone. It reads Apache Arrow IPC with pyarrow. It does not run a power flow, and it does not need the commercial Raptrix solver or a Rust toolchain.
MPL-2.0. Free to use, modify, and distribute.
Part of the open Raptrix suite. The authoritative wire contract stays in raptrix-cim-rs. This repository vendors one snapshot of that contract so a third party can check converter output on its own.
Python 3.12 or newer. Development and RHEL 10 use Python 3.12.10. The only runtime dependency is pyarrow.
Windows:
py -3.12 -m venv .venv
.venv\Scripts\python -m pip install -e ".[dev]"
.venv\Scripts\rpf-validate goldens\planning_tiny.rpfmacOS and Linux:
python3.12 -m venv .venv
.venv/bin/python -m pip install -e ".[dev]"
.venv/bin/rpf-validate goldens/planning_tiny.rpf".[dev]" installs pytest with the package. Omit .[dev] if you only want the commands.
Activate the virtual environment and the commands are rpf-validate and rpf-inspect.
rpf-validate goldens/planning_tiny.rpf
rpf-validate --json path/to/case.rpfPASS goldens/planning_tiny.rpf
0 error(s), 0 warning(s)
| Exit | Meaning |
|---|---|
| 0 | The file conforms. Warnings may still be printed. |
| 1 | A contract check failed, or a golden comparison did not match. |
| 2 | The path is missing or is not an Arrow IPC file. |
Each error has a stable code such as VERSION_UNSUPPORTED, MISSING_REQUIRED_TABLE, CASE_MODE_SOLVED_TABLES, DYNAMICS_VOCABULARY, BUS_ID_REFERENCE, or INVALID_ROW_COUNT. --json prints those codes.
A solved file adds one sentence before the error count. The numbers are the values stored in the file. They are not a judgment that the solution is physically correct.
PASS goldens/solved_tiny.rpf
Solved power flow (actual_solved): 4 bus voltages 1 pu, angle 0 deg; 2 in-service generators totaling 60 MW / 6 Mvar. Solver synthetic-0.
0 error(s), 0 warning(s)
rpf-inspect goldens/solved_tiny.rpf
rpf-inspect --json path/to/case.rpfThe first lines name the case and, when present, the stored solution:
solved_snapshot, 4 buses, 3 branches, 2 generators, fingerprint 33333333…
Solved power flow (actual_solved): 4 bus voltages 1 pu, angle 0 deg; 2 in-service generators totaling 60 MW / 6 Mvar. Solver synthetic-0.
The rest of the report lists the version stamp, case mode, solved-state presence, fingerprint, one logical row count per table, and feature flags. rpf-inspect describes the file even when validation would fail.
A file stamped with anything other than v0.14.5 fails. The code is stable:
FAIL path/to/case.rpf
VERSION_UNSUPPORTED version 'v0.14.4' is not supported; expected v0.14.5, 0.14.5
1 error(s), 0 warning(s)
The repository does not ship a broken golden. The test suite builds that failure from goldens/planning_tiny.rpf and checks the code.
rpf-validate and rpf-inspect stay the fast commands. rpf-health is optional. It inventories the model, counts islands, and lists structural notes. It does not run a power flow, and its warnings do not change the conformance result.
rpf-health goldens/planning_tiny.rpf
rpf-health --json path/to/case.rpfHealth report goldens/planning_tiny.rpf
conforms to v0.14.5
Inventory
4 buses, 3 branches (3 in service), ...
Topology
1 island (4 buses)
no isolated buses
Solved
solved tables: absent
Warnings
none
On a solved file the solved section repeats the stored-solution sentence and counts voltages outside the usual bands. v0.14.5 has no branch-flow columns, so the report says the balance check is skipped rather than inventing a residual.
An in-service branch or transformer is one whose status is true or non-zero. If that column is missing, the element is treated as in service. A three-winding transformer ties its three winding buses together. A fictional star bus is not an island by itself.
rpf-validate --golden goldens/solved_tiny.rpf path/to/candidate.rpfThis runs the contract checks, then compares logical content: case mode, table names, row counts, the stored fingerprint, and column values by name. Column order inside a table does not have to match. A match prints MATCH and exits 0. A difference prints DIFFER and exits 1.
The fingerprint is compared as a stored string. The validator does not recompute it.
from rpf_validator import compare, health_report, summarize, validate
report = validate("path/to/case.rpf")
if not report.ok:
for error in report.errors:
print(error.code, error.message)
summary = summarize("path/to/case.rpf")
print(summary.summary)
print(summary.solved)
print(health_report("path/to/case.rpf").to_text())
match = compare("path/to/candidate.rpf", "goldens/solved_tiny.rpf")validate raises RpfReadError when the path cannot be read. A readable file that fails the contract returns a report with ok false.
From the repository root, with the dev install above:
python -m pytestOn Windows, if the virtual environment is not activated:
.venv\Scripts\python -m pytestThe suite is local. It does not use a network, a solver, or any file outside this repository. The checks cover the three synthetic goldens, the command exit codes, and the cases that must fail: a bad version stamp, a missing required table, solved tables on a planning case, an illegal dynamics key, a bad row count, and a broken bus reference.
A pass means the file matches the vendored v0.14.5 reader contract.
- The version stamp is
v0.14.5or0.14.5. - The 18 canonical tables are present, plus
dc_converters, even when a table has zero rows. - Known tables match a contract column layout or a documented read dialect. Tables are matched by name.
- Case mode, solved-state presence, and the solved tables agree.
hour_ahead_advisoryis accepted and treated as a planning mode. - Dynamics parameters use
p1..pN.p0is rejected. A namedWTTQA1row must usepwr1..pwr4for its power breakpoints. - Non-null bus references on branches, generators, loads, and transformers point at
buses.
A pass does not mean the network solves, the voltages are credible, or the fingerprint was recomputed.
The full rule list and the snapshot pin are in docs/CONTRACT.md. The snapshot is raptrix-cim-rs commit 0d4d48f.
The files in goldens/ are synthetic. They contain no utility model and no customer data.
| File | What it shows |
|---|---|
goldens/planning_tiny.rpf |
flat_start_planning. 4 buses, 3 branches, 2 generators. |
goldens/contingency_tiny.rpf |
The same network plus one contingency. |
goldens/solved_tiny.rpf |
solved_snapshot with bus voltages and generator output. |
goldens/manifest.json records the expected case mode, fingerprint, and row counts for each file.
- raptrix-cim-rs is the source of truth for the schema contract.
- raptrix-psse-rs converts PSS/E into
.rpf. - raptrix-pslf-rs converts GE PSLF into
.rpf.
For the commercial Raptrix Power products, see raptrixpower.com.
Mozilla Public License 2.0. See LICENSE.