docs(historian): close #491 — read-back and EnsureTags proven against wonder-sql-vd03
The 2026-08-01 run closed every leg except read-back, which no reachable historian could
serve that day (the LAN instance accepts writes but serves no reads under a licence tag-count
violation; the licensed one needed the VPN). With the VPN up the run was repeated against
wonder-sql-vd03 and the remaining legs pass:
- EnsureTags provisioning: ensured=2, failed=0 — the path the LAN box could not exercise at
all (it is RemoteGrpc-only and that CAP was not listening).
- Read-back: two Modbus registers carrying DISTINCT NON-ZERO constants were historized, and
each read back as its own value (HR20 -> 8224, HR3 -> 120, quality 192). A first attempt
read back 0, which proves nothing — the same trap #536 recorded, so the proof was rebuilt
on values a crossed or fabricated answer could not fake.
Found during the run and FILED rather than fixed:
- #538 — one permanently-failing tag re-writes every healthy tag on every drain pass, forever.
DrainOnceAsync writes EVERY per-tag group and then acks all-or-nothing, so a tag whose
historian tag does not exist stops the FIFO head advancing while the healthy tags' values
are re-submitted every drain interval; the outbox never truncates (Capacity defaults to 0 =
unbounded, observed at 8.3 MB). The all-or-nothing ack is deliberate — RemoveAsync truncates
THROUGH an id, so partial acking could drop older unwritten entries — so the fix changes the
outbox contract and does not belong in this commit.
Also re-confirmed live: EnsureTags provisioning fires only for newly-ADDED historized tags, so
flipping an existing tag's historianTagname provisions nothing (Issue 5 of
2026-06-27-historian-gateway-integration-issues.md).
No production code changes — the recorder fix shipped in ad744734.
Claude-Session: https://claude.ai/code/session_015p7wGqy3YpZNCpDzTpGMKo
This commit is contained in:
@@ -929,9 +929,20 @@ to know:
|
||||
store-and-forward sink. A redundant pair therefore sends duplicate live values per historized tag.
|
||||
Deliberately recorded, not "fixed": gating it introduces a failover window with no capture.
|
||||
|
||||
Gate status: outbox append, drain, `WriteLiveValues` **accepted by a real historian**, and
|
||||
**restart-convergence** are all ✅. The final **read-back** hop is ❌ **not** proven — the LAN historian
|
||||
(`10.100.0.48`) accepts writes but serves no reads under a `License violation: Database tag count exceeds
|
||||
license tag count`, and the licensed `wonder-sql-vd03` needs the VPN. `EnsureTags` provisioning likewise
|
||||
could not run there (it is `RemoteGrpc`-only and that CAP is not listening). **Issue #491 stays open for
|
||||
the read-back hop alone**; treat the rest of continuous value-capture as live-proven.
|
||||
**Gate COMPLETE — #491 CLOSED 2026-08-04.** Outbox append, drain, `WriteLiveValues`,
|
||||
**restart-convergence**, `EnsureTags` provisioning (`ensured=2 failed=0`) and **read-back** all ✅. The
|
||||
read-back leg ran against the licensed `wonder-sql-vd03` with the VPN up: two registers carrying
|
||||
*distinct non-zero* constants (`8224`, `120`) each read back as its own value — a `0`-valued source
|
||||
would have proved nothing (the #536 trap).
|
||||
|
||||
⚠️ **A second defect was found and FILED, not fixed (#538): one permanently-failing tag re-writes every
|
||||
healthy tag on every drain pass, forever.** `DrainOnceAsync` writes **every** per-tag group and then acks
|
||||
**all-or-nothing**, so one bad tag stops the FIFO head advancing while the good tags' values are
|
||||
re-submitted to the historian on every retry — duplicate samples, and an outbox that never truncates
|
||||
(`Capacity` defaults to `0` = unbounded; observed at 8.3 MB). The all-or-nothing ack is deliberate
|
||||
(`RemoveAsync` truncates *through* an id, so partial acking could drop older unwritten entries) — the
|
||||
consequence is what is undocumented.
|
||||
|
||||
Also re-confirmed live: **`EnsureTags` provisioning fires only for newly-ADDED historized tags** —
|
||||
flipping an existing tag's `historianTagname` produces no provisioning at all
|
||||
(`2026-06-27-historian-gateway-integration-issues.md` Issue 5).
|
||||
|
||||
Reference in New Issue
Block a user