feat: report foreign chain RPC provider health at Node startup - #4071
feat: report foreign chain RPC provider health at Node startup#4071haiyuechen-nearone wants to merge 8 commits into
Conversation
36311f1 to
4ff2996
Compare
4ff2996 to
c42d937
Compare
b060ade to
8b6edca
Compare
Pull request overviewWires the existing Changes:
Reviewed changesPer-file summary
FindingsBlocking (must fix before merge):
Non-blocking (nits, follow-ups, suggestions):
|
8b6edca to
6023892
Compare
|
@claude review |
Pull request overviewWires the existing Since the previous review round both blocking items were addressed: Changes:
Reviewed changesPer-file summary
FindingsBlocking (must fix before merge):
Non-blocking (nits, follow-ups, suggestions):
Still open from the previous round, no need to re-litigate: the |
Since we expect the operator to correctly configure all fields in the config file, not adding expected network fingerprint is considered "incorrect" and causes us to not know if a provider is healthy or not/ |
35b22c4 to
9ec4b44
Compare
Spawns the probe detached, so it reports which network each provider serves without delaying startup or gating anything. A status carries no provider text and no auth material, so it is logged whole.
Publishes `mpc_foreign_chain_rpc_providers_configured` and `mpc_foreign_chain_rpc_providers_healthy`, labelled by chain rather than by provider, since a provider name is operator chosen and would put an unbounded label on a time series. `ForeignChain::label()` is the one place the chain label lives, so a metric label and a config key cannot drift apart. An e2e test points one node at a mock serving the expected chain id and another at the same mock while expecting a different network, so the gauges separate a healthy provider from one on the wrong network end to end. The EVM mock answers `eth_chainId` to make that possible. Leaves a provider no probe covers out of the `x/y providers healthy` summary. It counted toward the denominator but could never reach the numerator, so a node configuring a chain without a probe read as permanently degraded.
A chain no probe covers no longer publishes gauges, and an empty foreign chains config no longer warns on every boot. The panic guard is gone: the deployed binary aborts on panic, so it never ran. The summary is a value now, asserted directly instead of through log lines, and a node config test pins every chain's config key to its label.
A node is expected to configure the chains the code supports, so an empty section is a misconfiguration rather than a quiet path. The startup probe is the only place that observes it.
The warning named our own mechanism and left the operator to work out which of their chains went unchecked; it now lists them. The docs claimed a `ton` section exists, and that chains without an inspector report a status name an operator never sees.
`ProbeReport` gains `From<Vec<ProviderHealth>>`, so the gauge tests no longer open sockets and drive another crate's probe just to reach this crate's publication. They now cover several chains in one report, and pin the label of the one chain whose key is not its variant name. Log lines carry the chain's config key rather than its variant name, and a healthy or uncheckable provider logs at info, so the documented line per provider appears at the level operators run. Also drops metric labels from the truncation rationale: no metric carries a fingerprint.
9ec4b44 to
b25b5e2
Compare
Keep only the claim the fixture does not make, and leave the Given and When markers bare.


Closes #4094.
The node now spawns
probe_all_providersas a detached task at startup. An e2e test is added to validate the code through asserting metrics emitted.Notes for review
The status of each provider is logged: This is safe because
ProviderStatusrenders no upstream text, and the observed fingerprint from provider response is length capped.The metric gauges are labelled per chain: We are interested in if a chain can be served from by a Node. Logs can be used to figure out exactly which provider is down.
Probing for Ethereum, Solana and TON is not implemented
A completely empty
foreign_chainssection would produce a warn log.