v2.54.4
v2.54.4
Persistence-safety hardening — generalizes issue #71 to the analysis state stores.
A multi-agent audit found several state files whose readers swallow a
JSONDecodeError and reset to an empty default, so a later read-modify-write
writes back only the new field and silently wipes prior data. Atomic writes alone
can't help, because the loss happens at read time.
Fixed
- Read-modify-write paths now read strictly and refuse to overwrite a corrupt
existing file (sharedConfigParseError+_read_json_strict) instead of
clobbering it:- media-analysis preferences — 5 write paths (set-defaults, timed-marker
default, sampling-mode default, AI governance, caps preset) - update-state — configure/clear update settings (3 paths), now also written
atomically (temp +os.replace) - per-clip corrections — the human edit history (highest-value store);
update and revert paths
- media-analysis preferences — 5 write paths (set-defaults, timed-marker
- Non-atomic writes a crash could truncate now use temp +
os.replace: the bin
summary markdown and Fusion.settingfiles. - A read-modify-write race on
analysis.jsonunder the threaded control panel is
serialized under the existing state lock, so a concurrent transcript regen or
batch report write can't drop the other's updates. - Read-only callers keep their forgiving fallback (defaults, never write).
Validation
- Full offline unit/static suite green (1256 tests), including new
tests/test_persistence_safety.py(strict-read refuse-to-clobber + atomic
writers). Pure Python state-handling; no Resolve behavior changed, so no live
run required. (The PS9 lock is dashboard threading, not the Resolve API.)