- cef_universe_run.py: resumable batch over all 295 CEFs ->
cef_annual_all.json (241 parsed, actual per-share character).
- cef_rank_all.json: 239-fund ranking, actual char x (t5 + 0.4 vol5);
surfaces FXBY and DPG beyond the original shortlist.
- share fractions now use the component sum as denominator (always
sum to 1); dist_tot remains the validity gate. Fixes CEE-style
111% sums when the NAV-identity fallback total is short.
- server watchdog + app CEF tab; RESEARCH.md updated.
- Fund Lab tab: CEF tax-arb shortlist table (char actual-vs-model,
discount, 5y return/vol, scenario hits, tenders, score) built from
cef_character.json + cef_annual.json.
- fundlab/server_watchdog.sh: relaunches Streamlit on :8599 if the
health endpoint stops answering (the old watchdog only covered the
overnight screen and had exited).
- fundlab/cef_universe_run.py: resumable batch extending per-share
verification to all 295 CEFs -> cef_annual_all.json.