# KOPR R130 — WPlanner performance release gate and Markdown cleanup

**Base build:** `KOPR_CLEAN_BUILD_20260729_R129_WPLANNER_DEFERRED_PERSISTENT_CACHE.zip`  
**Date:** 2026-07-29  
**Scope:** final R125–R130 performance gate, deterministic reference scenarios, consolidated documentation and clean packaging. No scientific-model change.

## Summary

R130 closes the WAnalyzer/WPlanner remediation sequence. It adds one final platform-neutral gate covering the complete production routing introduced in R125–R129 and replaces the accumulated per-release Markdown files with a small set of authoritative, topic-oriented documents.

The release does not change:

- WPlanner N-body dynamics, DE440s, Cowell equations or DOP853 tolerances;
- date-aware element/apparition selection;
- light-time or topocentric geometry;
- provenance or Cancel semantics;
- WVisual, WCCD or WStack numerical paths;
- WAnalyzer/WComparison two-body photometric equations.

## Final WPlanner contract

The new `wplanner_performance_release_gate.py` enforces:

1. `EphemGen()` and `PlotGen()` execute through immutable operations on the shared background QThread runner.
2. `wplanner.py` contains no `QApplication.processEvents()` and no direct heavy compute calls.
3. Progress is signal-routed and elapsed time uses `QTimer`.
4. One operation owns at most one spawn process pool; workers cannot create nested pools.
5. One job owns one comet/apparition interval and at most one forward and one backward integration.
6. Planner element batches use one vector Astropy frame-transform call.
7. Persistent fitting, validation, compression and writing are deferred through a bounded single-worker service.
8. Persistence failure, queue saturation or shutdown timeout cannot invalidate a completed ephemeris.
9. WPlanner remains N-body with persistent validated segments.
10. WStack remains serial and does not use persistent segment cache or process workers.
11. WAnalyzer prepared-plot snapshots, revision checks and one-shot missing-curve recovery remain active.

## Deterministic scenarios

`benchmark_wplanner_r130.py` and `tests/data/wplanner_performance_reference_r130.json` define the final call-count contract:

| Scenario | Interval jobs | Automatic workers |
|---|---:|---:|
| one comet × four midnights | 1 | 1 |
| one comet × 500 epochs | 1 | 1 |
| four comets × 300 epochs | 4 | 4 |
| 300 comets × four epochs | 300 | 4 |

The synthetic persistent-cache probe requires:

```text
cold interval: 1 integration
warm covered interval: 0 integrations
background persistence: drained successfully
```

Wall time, CPU utilisation and RSS remain target-system diagnostics and are not portable pass/fail thresholds.

## Markdown cleanup

Before R130:

```text
QA Markdown files:    208
CLEAN Markdown files: 91
```

After R130:

```text
QA Markdown files:    12
CLEAN Markdown files: 5
```

The CLEAN archive now contains only:

- `README.md`;
- `docs/CHANGELOG.md`;
- `docs/COMET_DESIGNATION_USER_GUIDE.md`;
- `docs/SCIENTIFIC_COMPACT_USER_GUIDE.md`;
- `docs/SCIENTIFIC_PHOTOMETRY_POLICY.md`.

The QA archive adds:

- `README_QA.md`;
- `RUN_R130_FOCUSED_QA.md`;
- five consolidated developer documents covering modal ephemerides, WPlanner performance, Analyzer/Comparison analysis, performance validation and photometry conventions.

Obsolete top-level release reports, old `RUN_Rxxx` instructions, duplicated implementation notes and the historical `docs/developer/release_reports/` tree were removed. Historical traceability remains in `docs/CHANGELOG.md`, source-control history and versioned test module names.

`documentation_hygiene.py` now enforces the exact Markdown layout independently for QA and CLEAN distributions.

## QA

The complete QA archive was executed in eight non-overlapping groups:

```text
1767 passed
8 skipped
0 failed
```

The eight skips require a complete optional PyQt5 or Astropy FITS/time runtime.

Final release checks:

```text
analysis_release_gate.py:             PASS
modal_ephemeris_release_gate.py:      PASS
wplanner_performance_release_gate.py: PASS
documentation_hygiene.py:             PASS
validate_performance_release.py:      PASS
```

Final manifest sizes:

```text
QA SHA256SUMS:    342 files
CLEAN SHA256SUMS: 95 files
```

Both manifests and both ZIP archives were verified after removal of runtime caches and bytecode files.

## Target-system validation still required

The build environment does not contain the full production PyQt5, Astropy, `jplephem`, DE440s and representative 300-comet runtime. On the target installation, record:

- first-run and warm-cache time for one comet × four midnights;
- one comet × 500 epochs;
- four comets × 300 epochs;
- 300 comets × four epochs;
- worker utilisation with 1, 2 and 4 workers;
- Cancel during integration and deferred persistence;
- peak RSS and cache size;
- numerical comparison with R129.
