docs+chore(localdb): phase-2 rig config + docs
Enables the alarm store-and-forward sink on all four driver nodes of the docker-dev rig -- the replicating site-a pair and the default-OFF site-b pin -- so the live gate has a real buffer to watch converge, and can see that site-b's sink works as a plain node-local queue with no peer traffic. Two rig details worth stating rather than rediscovering. The endpoint is deliberately unresolvable: there is no HistorianGateway here, so every drain attempt fails, which is exactly the historian-outage state the buffer exists for. But it still has to be a syntactically valid absolute http(s) URI or the host refuses to start, because ServerHistorianOptionsValidator is consumer-gated -- AlarmHistorian:Enabled=true makes the endpoint required even while ServerHistorian:Enabled=false. And MaxAttempts is raised far above the production default of 10, which against a permanently unreachable gateway would dead-letter the entire queue about five minutes in, turning a buffering test into a dead-letter test. Docs record what an operator now has to know: that a rising queue depth on a Secondary is correct and on BOTH nodes is not (that shape is a redundancy snapshot naming neither node -- check node identity before suspecting the sink), that delivery is at-least-once across a failover by design with no dedup layer, and that AlarmHistorian:DatabasePath is removed but should be left in place through the upgrade because the migrator still reads it to find the file to copy. Claude-Session: https://claude.ai/code/session_01GASWkNEi68FSCtvr6rLoEW
This commit is contained in:
@@ -328,6 +328,22 @@ services:
|
||||
# site-a-1 is the initiator: it binds the h2c sync listener on 9001 AND dials the peer.
|
||||
# Setting SyncListenPort makes Program.cs add a dedicated Http2-only Kestrel listener and
|
||||
# re-bind the primary HTTP port (an explicit Listen* otherwise discards ASPNETCORE_URLS).
|
||||
# Alarm store-and-forward buffer, Phase 2. Enabled on BOTH halves of the pair so the
|
||||
# buffer is a live, replicated table rather than an empty one — the live gate needs a real
|
||||
# queue to watch converge, and needs to see that only the Primary drains it.
|
||||
#
|
||||
# There is no HistorianGateway on this rig, so the endpoint below is deliberately
|
||||
# unresolvable: every drain attempt fails, which is exactly the historian-outage state the
|
||||
# buffer exists for. Note the endpoint must still be a syntactically valid absolute http(s)
|
||||
# URI or the host refuses to start — ServerHistorianOptionsValidator is consumer-gated, so
|
||||
# AlarmHistorian:Enabled=true makes it required even while ServerHistorian:Enabled=false.
|
||||
#
|
||||
# MaxAttempts is raised far above the production default of 10. With a permanently
|
||||
# unreachable gateway the default would dead-letter the whole queue about five minutes into
|
||||
# the outage, turning a buffering test into a dead-letter test.
|
||||
AlarmHistorian__Enabled: "true"
|
||||
AlarmHistorian__MaxAttempts: "1000000"
|
||||
ServerHistorian__Endpoint: "${OTOPCUA_HISTORIAN_ENDPOINT:-http://histgw-absent.invalid:5222}"
|
||||
LocalDb__Path: "/app/data/otopcua-localdb.db"
|
||||
LocalDb__SyncListenPort: "9001"
|
||||
LocalDb__Replication__PeerAddress: "http://site-a-2:9001"
|
||||
@@ -365,6 +381,22 @@ services:
|
||||
# but does NOT dial (no PeerAddress). The replication stream is bidirectional, so a-1's
|
||||
# single dial carries both directions. Same key + MaxBatchSize as a-1 (byte-identical key
|
||||
# is mandatory — the interceptor fail-closes on a mismatch).
|
||||
# Alarm store-and-forward buffer, Phase 2. Enabled on BOTH halves of the pair so the
|
||||
# buffer is a live, replicated table rather than an empty one — the live gate needs a real
|
||||
# queue to watch converge, and needs to see that only the Primary drains it.
|
||||
#
|
||||
# There is no HistorianGateway on this rig, so the endpoint below is deliberately
|
||||
# unresolvable: every drain attempt fails, which is exactly the historian-outage state the
|
||||
# buffer exists for. Note the endpoint must still be a syntactically valid absolute http(s)
|
||||
# URI or the host refuses to start — ServerHistorianOptionsValidator is consumer-gated, so
|
||||
# AlarmHistorian:Enabled=true makes it required even while ServerHistorian:Enabled=false.
|
||||
#
|
||||
# MaxAttempts is raised far above the production default of 10. With a permanently
|
||||
# unreachable gateway the default would dead-letter the whole queue about five minutes into
|
||||
# the outage, turning a buffering test into a dead-letter test.
|
||||
AlarmHistorian__Enabled: "true"
|
||||
AlarmHistorian__MaxAttempts: "1000000"
|
||||
ServerHistorian__Endpoint: "${OTOPCUA_HISTORIAN_ENDPOINT:-http://histgw-absent.invalid:5222}"
|
||||
LocalDb__Path: "/app/data/otopcua-localdb.db"
|
||||
LocalDb__SyncListenPort: "9001"
|
||||
LocalDb__Replication__ApiKey: "dev-site-a-localdb-sync-key"
|
||||
@@ -397,6 +429,11 @@ services:
|
||||
# site-b is the default-OFF pin: it gets the pair-local cache but NO SyncListenPort and NO
|
||||
# replication config, so no sync listener binds and ISyncStatus stays disconnected/Healthy.
|
||||
# This is what the live gate's check 8 verifies — the cache works locally with replication off.
|
||||
# Alarm store-and-forward with replication OFF — the other half of the site-b pin. The sink
|
||||
# must work as a plain node-local buffer here, with no sync listener and no peer traffic.
|
||||
AlarmHistorian__Enabled: "true"
|
||||
AlarmHistorian__MaxAttempts: "1000000"
|
||||
ServerHistorian__Endpoint: "${OTOPCUA_HISTORIAN_ENDPOINT:-http://histgw-absent.invalid:5222}"
|
||||
LocalDb__Path: "/app/data/otopcua-localdb.db"
|
||||
ports:
|
||||
- "4844:4840"
|
||||
@@ -422,6 +459,11 @@ services:
|
||||
Serilog__MinimumLevel__Override__Microsoft.AspNetCore: "Warning"
|
||||
GALAXY_MXGW_API_KEY: "${GALAXY_MXGW_API_KEY:-mxgw_otopcua2_GI7-tNozYE6cXGUSgEzL3AHDV7bYcYIHdMwKYgyHdX4}"
|
||||
# site-b default-OFF pin (see site-b-1): cache on, replication off.
|
||||
# Alarm store-and-forward with replication OFF — the other half of the site-b pin. The sink
|
||||
# must work as a plain node-local buffer here, with no sync listener and no peer traffic.
|
||||
AlarmHistorian__Enabled: "true"
|
||||
AlarmHistorian__MaxAttempts: "1000000"
|
||||
ServerHistorian__Endpoint: "${OTOPCUA_HISTORIAN_ENDPOINT:-http://histgw-absent.invalid:5222}"
|
||||
LocalDb__Path: "/app/data/otopcua-localdb.db"
|
||||
ports:
|
||||
- "4845:4840"
|
||||
|
||||
Reference in New Issue
Block a user