Skip to content

docs(debug-journal): fold in the 2026-09-22 queue slice; correct the component-thread and shared-fixture entries - #5192

Merged
springfall2008 merged 1 commit into
mainfrom
bot/debug-journal-2026-09-22
Sep 23, 2026
Merged

springfall2008 merged 1 commit into
mainfrom
bot/debug-journal-2026-09-22

Conversation

@springfall2008

Copy link
Copy Markdown
Owner

Automated journal flush — the triage bot folding the day's queued findings into tools/debug-journal.md and re-checking existing entries against what has merged since (verified against main 8b9fe029). A human merge is the review gate. 55 candidates remain queued.

Folded in (10):

  • GH#4993 follow-up (SolaX 10402 token thrash) — rewrote the SolaX row. 10402 repeating every cycle with data still flowing is server-side token invalidation between cycles (same token succeeds mid-cycle and is rejected next cycle; stated ~30-day expires_in vs real ~1-cycle token lifetime); prime suspect a second client sharing the same client_id/secret — kept marked suspected, not proven. Each 10402 also inflates the component's lifetime error counter. Secondary finding: "No solar forecast data was returned from HA sensors" on the SolaX Cloud template = no PV forecast source configured at all (the template's pv_forecast_* regexes match nothing without the Solcast HA integration). Code claims re-verified on 8b9fe029: the solax.py auth-error branch clears the token and request_wrapper() retries in-request; the solcast.py HA-sensor fall-through branch; the templates/solax_cloud.yaml regexes.

  • GH#5087 (Solis API codes misclassified) — fixed on main since the candidate was written (PR fix(solis): stop retries draining the SolisCloud daily API allowance #5089, merged 2026-09-14): B0115/R0000 are now classified (SOLIS_API_CODES, SOLIS_API_CODES_NO_RETRY) with a per-inverter datalogger-offline cooldown, and automatic_config() now retries via automatic_config_done instead of the first-cycle-only gate. Folded as a fixed entry with the pre-fix(solis): stop retries draining the SolisCloud daily API allowance #5089 mechanism kept (B0115 was treated as rate limiting, R-series fell through to "Unknown code" with the full retry ladder, draining the 200/day allowance).

  • GH#5090 (Solis amp↔watt voltage) — fixed on main since the candidate was written (PR fix(solis): use a stable voltage for amp<->watt conversions #5095, merged 2026-09-15): get_nominal_voltage() priority is now solis_nominal_voltage → HV live (>60V) → BMS charge-voltage classification (16S/15S) → 48V fallback. The pre-fix diagnostic (failed-write readbacks at a constant ratio of the target) is kept for older logs; pre-fix(solis): use a stable voltage for amp<->watt conversions #5095 there was no workaround, since solis_nominal_voltage fed only the capacity path.

  • GH#5091 (auto-config first-cycle gate) — fixed by the same PR fix(solis): stop retries draining the SolisCloud daily API allowance #5089 (automatic_config_done retry). Folded with Solis: one unreachable inverter keeps the whole component in startup backoff #5093's premise correction (auto-config actually ran at the end of every completed first attempt regardless of poll_success — now moot since the gate is gone). GE Cloud still runs its auto-config under if first: only, noted so its self-heal after an outage is described as the slow one.

  • GH#5093 (per-inverter failures folded into one poll_success) — still live on main; folded as still-live with the workaround (list only working SNs in solis_inverter_sn) and the contained fix shape (per-inverter booleans already exist at every poll_success site). PR Solis: don't let a refused startup register read abort startup, and back off B0600 #5185 (open, unmerged) noted as the neighbouring per-inverter startup_reset_registers() backoff.

  • GH#5092 (bare ValueError for a missing load source) — new symptom-table row: fetch_sensor_data()'s bare raise ValueError unwinds the whole cycle (the fetch-before-inverter-read ordering is what makes "SoC stops updating"); cloud components set load_today at runtime, so "fix apps.yaml" is the wrong pointer during a component startup delay; no fallback exists before a first successful fetch.

  • GH#5094 (Tesla discharge-stop fallback) — appended to the HA write/verify row: adjust_charge_immediate()'s fallback to charge_stop_service with domain="discharge" lands on active discharge to load on Tesla, so freeze/hold cycles issue a discharge command then a hold ~2s later. Re-verified on 8b9fe029 (inverter.py:3089-3090); workaround plus the repeat: False caveat kept.

  • GH#5082 (GEC 3-phase freeze export) — appended to the GE Cloud row: inv_support_discharge_freeze is read statically from INVERTER_DEF while inv_has_timed_pause is runtime-probed, so set_export_freeze is never force-disabled for the eco-less 3-phase class; the "grep only for the eco warning" trap noted; the GIV-3HY charge_power_rate-limits-AC-only point kept as hardware-reported; fix precedent PR feat(fox): select Feed-in First for a Fox Cloud freeze export #5038.

  • GH#5083 (hold hysteresis unreachable) — new symptom row: the hold gate has no tolerance, the nested 1% hysteresis is unreachable and its else re-enables the window, so ±1% SoC quantisation wobble thrashes charge/hold writes; confirmation recipe and "don't hunt for a v8.53 regression" kept. Structure re-verified on 8b9fe029 (line numbers drifted, structure identical).

  • GH#5079 pointers — folded into the rewritten Test-order section: hand-rolled args snapshot/restore remains in test_inverter.py/test_agent_tools.py (≥9 modules at write time — the others were cleaned up); soc_kwh_history = {} restore-to-default in test_calculate_yesterday.py remains latent-fragile; the runner still breaks on first failure.

Existing entries corrected (2 areas):

  • Component health row — the entry said ComponentBase.start() runs every component's run() loop "on the main asyncio event loop" and concluded a blocking sync call stalls shutdown, HA callbacks and every other component. Wrong on both counts (candidate 5075, from the PR Run ML training off the event loop and let a shutdown abandon it #5112 review). Re-verified on 8b9fe029: Components.start() starts each component through base.create_task(), which spawns a real non-daemon OS thread per component running its own asyncio.run() — a sync CPU-bound call blocks only that component's loop; the real cost is shutdown, where stop_all() does t.join(5 * 60) per thread after terminate() and the interpreter's non-daemon-thread shutdown then waits again unbounded. PR Run ML training off the event loop and let a shutdown abandon it #5112 (open draft, unmerged) is the fix; the misleading "Lock released" comment is still on main.

  • Test-order pollution section + Test-ordering trap bullet — the section said all tests share one PredBat fixture; PR test: give each test its own PredBat rather than sharing one (#5079) #5102 (merged 2026-09-15) gave every registry test its own instance and create_predbat() now pins minutes_now/now_utc from FIXTURE_MINUTES_NOW, closing the GH#5026 wall-clock class the entry had anticipated. References to tools/shuffle_fuzz_known_pairs.txt removed (the file no longer exists). Historical mechanism kept for older logs; the candidate's residue pointers folded in.

Dropped (4) — already covered by existing entries:

  • 5071 (debug snapshot ~5MB + unbounded download-all): both halves already in the journal (the debug_history_count max raise with storage arithmetic, and the web download route capped at 16 by PR Raise debug_history_count maximum to 500 for multi-week history (#5070) #5071).

  • 5072 (retrain interval vs the 48h staleness cap): already in the Load ML row's "frequency is a separate axis" paragraph.

  • 5073 (SolarEdge preserve-charge refusals): core already in the symptom row (idle-reset writes; no failure dedup in write_and_poll_value()); only two case notes folded in (SE preserve flag invisible in dumps; unexplained second execute pass ~46s later).

  • 5074 (chat OpenRouter-first error wording): already in the Web/MCP/Chat row.

Quality-gate note: the cspell/markdownlint/black hooks pass (&& gates the quick suite on them); the quick suite then aborted at test_teslemetry_local_weekday_follows_the_base_clock at 00:09 BST — the journal's own documented local-midnight clock-window failure (docs-only tree, second sighting), unrelated to these docs-only changes.

🤖 Generated with Claude Code

…component-thread and shared-fixture entries

Co-Authored-By: Claude Code <noreply@anthropic.com>
@springfall2008
springfall2008 marked this pull request as ready for review September 23, 2026 21:15
Copilot AI lite review requested due to automatic review settings September 23, 2026 21:15
@springfall2008
springfall2008 merged commit 8de140d into main Sep 23, 2026
2 checks passed

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copilot wasn't able to review any files in this pull request.


💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants