Skip to content

docs: Add section in onboarding doc about foreign chain configs - #4097

Merged
anodar merged 3 commits into
mainfrom
4023-document-expected-operator-foreign-chain-rpc-configurations
Aug 7, 2026
Merged

docs: Add section in onboarding doc about foreign chain configs#4097
anodar merged 3 commits into
mainfrom
4023-document-expected-operator-foreign-chain-rpc-configurations

Conversation

@anodar

@anodar anodar commented Aug 7, 2026

Copy link
Copy Markdown
Contributor

closes #4023

@claude

claude Bot commented Aug 7, 2026

Copy link
Copy Markdown

PR title type suggestion: This PR updates both documentation and a configuration file. Consider using chore: instead of docs: to reflect that it includes config changes alongside the markdown updates.

Suggested title: chore: Add section in onboarding doc about foreign chain configs

@claude

claude Bot commented Aug 7, 2026

Copy link
Copy Markdown

Pull request overview

This PR expands the operator-facing foreign-chain RPC documentation: deployment/cvm-deployment/user-config.toml gains a full per-chain provider matrix (public + Alchemy + QuickNode, plus Geomi for Aptos) for Bitcoin, Abstract, Starknet, Aptos and Sui, with a commented mainnet variant replacing the previous inline # mainnet: … hints; the TDX onboarding guide gains a new "Foreign chain RPC providers" section reproducing the same matrix for testnet and mainnet, plus where to get API keys and how to verify with foreign-chain-config-tester. All fingerprint values match the canonical table in docs/foreign-chain-transactions.md:669-679 and the golden set in crates/foreign-chain-health-check/src/golden.rs, and the Sui header-only auth rule matches the validation in crates/node-config/src/foreign_chains.rs:92-97. Documentation-only; no code changes.

Changes:

  • user-config.toml: adds Alchemy/QuickNode providers for Abstract and Starknet, adds whole new aptos and sui sections, renames the abstract-testnet/publicnode providers to public
  • user-config.toml: replaces the inline # mainnet: … fingerprint hints in the foreign_chains block with a ~100-line commented mainnet variant at the end of the file
  • running-an-mpc-node-in-tdx-external-guide.md: new ### Foreign chain RPC providers section with API-key sources, auth caveats, a config-tester pointer, and full testnet/mainnet TOML blocks
  • running-an-mpc-node-in-tdx-external-guide.md:785: drops foreign_chains from the "inherited from the template" list and cross-links the new section

Reviewed changes

Per-file summary
File Description
deployment/cvm-deployment/user-config.toml Full testnet provider matrix for 5 chains with path/header auth blocks; commented mainnet variant appended
docs/running-an-mpc-node-in-tdx-external-guide.md New "Foreign chain RPC providers" section (testnet + mainnet TOML), cross-link from the config snippet

Findings

Blocking (must fix before merge):

  • docs/running-an-mpc-node-in-tdx-external-guide.md:849 and :953both guide TOML blocks drop expected_network_fingerprint, which the template sets for every chain. Line 785 now points operators at this section as the source for the foreign_chains block, and line 830 enumerates the required per-chain keys as only timeout_sec, max_retries and providers — so an operator who follows the guide ends up with no fingerprint on any chain. That field is the only thing that catches a provider pointed at the wrong network, which is precisely the mistake the new testnet/mainnet split invites (e.g. an Alchemy app created on mainnet while the rest of the config is testnet). Nothing reads it at runtime today (crates/node-config/src/foreign_chains.rs:52-55; the only consumer is probe::probe_all_providers, not yet wired into the node), but docs/foreign-chain-transactions.md:697-699 states the contract explicitly: "leaving it unset is not a silent skip: every provider of the chain is reported as MissingExpectedFingerprint". Please add the field to both blocks, matching the template:

    [mpc_node_config.node.foreign_chains.abstract]
    timeout_sec = 30
    max_retries = 3
    expected_network_fingerprint = "11124"   # mainnet: "2741"

    (testnet: bitcoin 000000000933ea01ad0ee984209779baaec3ced90fa3f408719526f8d77f4943, abstract 11124, starknet 0x534e5f5345504f4c4941, aptos 2, sui 69WiPg3DAQiwdxfncX6wYQ2siKwAe6L9BZthQea3JNMD; mainnet values already in the template.) Line 830's list of required keys needs the same addition.

  • docs/running-an-mpc-node-in-tdx-external-guide.md:840 — the warning against embedding a key directly in rpc_url understates the consequence, in the one place where an operator decides whether the kind = "path" ceremony is worth it. It says the key "will be logged in plain text on policy mismatch errors" (true — foreign_chain_whitelist_verifier.rs logs local_rpc_url inside BaseUrlMismatch/ChainRoutingMismatch), but the larger exposure is that register_foreign_chains (crates/node/src/coordinator.rs:1051) submits configured_chains() — the provider URLs — as arguments of a public NEAR function call. AuthConfig::Path is what strips the token from that URL (configured_chainsstrip_placeholder); with the key inlined and no path auth it is published in NEAR transaction history, permanently. Suggested wording: "…without kind = "path": the node registers its provider URLs on-chain, so an inlined key ends up in public NEAR transaction arguments (and in node logs on whitelist-mismatch warnings). kind = "path" strips the token before registration."

Non-blocking (nits, follow-ups, suggestions):

  • deployment/cvm-deployment/user-config.toml:6-11 — the header's "MUST be replaced with real values before deploying" list wasn't extended with the new YOUR_ALCHEMY_API_KEY / YOUR_QUICKNODE_API_KEY / YOUR_GEOMI_API_KEY / YOUR-SLUG placeholders. It also promises "The placeholders below are intentionally non-hex so a forgotten swap fails loudly at node startup", which does not hold for these: nothing validates token values, so an unedited template deploys cleanly and registers 8 of 13 providers that will only ever 401. Worth adding them to the list (and noting that the failure is silent), or shipping the key-bearing providers commented out so the default template stays deployable as-is.
  • deployment/cvm-deployment/user-config.toml:3-4 — "Inline # mainnet: ... comments below show the value to use when running on mainnet instead" no longer describes the foreign_chains block, which now uses the commented mainnet variant at line 257. Only chain_id (:57) and mpc_contract_id (:104) still work that way.
  • docs/running-an-mpc-node-in-tdx-external-guide.md:785 — "use the full per-network provider set in [Foreign chain RPC providers]" reads as add, but the guide's blocks and the template's foreign_chains sections are the same TOML tables; pasting one alongside the other is a duplicate-key parse error. Suggest "…replace the template's foreign_chains sections with the per-network set in …".
  • deployment/cvm-deployment/user-config.toml:161, :185, :209 (and the guide's copies) — provider names are matched against the on-chain whitelist by exact ProviderId (crates/node/src/foreign_chain_whitelist_verifier.rs:126-134). This PR renames abstract-testnetpublic and publicnodepublic and introduces quicknode/geomi. It is log-only today, but if the voted allowed_foreign_chain_providers entries use different IDs, every operator following this template gets a ProviderNotInWhitelist warning per provider. Worth confirming these names match the whitelist that has been (or will be) voted in.
  • deployment/cvm-deployment/user-config.toml:257-380 — the provider matrix now exists in four near-identical copies (template active, template commented-mainnet, guide testnet, guide mainnet). Everything except URL and fingerprint is byte-identical, and the two documents already disagree on expected_network_fingerprint (first finding), which is exactly how that drift shows up. Consider having the template's mainnet block link to the guide section rather than inlining a second full copy.
  • deployment/cvm-deployment/user-config.toml:178 (and guide :884, plus the mainnet copies) — the Alchemy Starknet URL pins …/rpc/v0_10/. Provider-side RPC spec versions get retired, so this will rot silently; a short note that the version segment comes from the Alchemy dashboard would age better than the pinned value alone.
  • deployment/cvm-deployment/user-config.toml:237, :252 — the Sui public provider spells out auth.kind = "none" while the public providers of the other four chains omit the block entirely. Both parse to AuthConfig::None; just inconsistent within one file.

⚠️ Issues found

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.

Pull request overview

Adds operator-facing documentation and template updates to clarify which foreign chains and RPC providers MPC node operators are expected to configure (testnet + mainnet), aligning with the need to validate verify_foreign_transaction requests across supported chains.

Changes:

  • Added a “Foreign chain RPC providers” section to the TDX external running guide, including full example foreign_chains TOML blocks for testnet and mainnet plus auth guidance.
  • Expanded and clarified deployment/cvm-deployment/user-config.toml foreign chain template comments and provider entries (incl. Alchemy/QuickNode/Geomi, and a commented mainnet variant block).

Reviewed changes

Copilot reviewed 2 out of 2 changed files in this pull request and generated 2 comments.

File Description
docs/running-an-mpc-node-in-tdx-external-guide.md Adds the new foreign-chain RPC provider documentation and copy/paste TOML examples for operators.
deployment/cvm-deployment/user-config.toml Updates the shipped operator template to include/describe the expected foreign-chain provider setup and a mainnet variant.
Suppressed comments (2)

docs/running-an-mpc-node-in-tdx-external-guide.md:968

  • In the Mainnet example, Abstract uses providers.public, but the deployment/cvm-deployment/user-config.toml mainnet variant uses providers.abstract-mainnet. If operators start from the template (as recommended earlier in the guide) and paste this snippet, it can create duplicate URLs and fail config validation. Use the template’s provider table name here.
[mpc_node_config.node.foreign_chains.abstract.providers.public]
rpc_url = "https://api.mainnet.abs.xyz"

docs/running-an-mpc-node-in-tdx-external-guide.md:989

  • In the Mainnet example, Starknet uses providers.public, but the user-config.toml template uses providers.publicnode. To prevent duplicate-URL validation failures when operators merge this with the template, match the provider name used by the template.
[mpc_node_config.node.foreign_chains.starknet.providers.public]
rpc_url = "https://starknet-rpc.publicnode.com"

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment thread docs/running-an-mpc-node-in-tdx-external-guide.md Outdated
Comment thread docs/running-an-mpc-node-in-tdx-external-guide.md Outdated
netrome
netrome previously approved these changes Aug 7, 2026

@netrome netrome left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

Thank you for documenting this 🙏

> **Important:**
>
> * The placeholder string in `rpc_url` must exactly match the `placeholder` value (case-sensitive). Do not embed an API key directly in `rpc_url` without `kind = "path"` — it will be logged in plain text on policy mismatch errors.
> * **Sui is different from the other chains:** the node talks to Sui over gRPC, so API keys cannot go in the URL — only header auth (or none) works. Alchemy takes the key as an `Authorization: Bearer` header, QuickNode as an `x-token` header on port `9000`. Use the exact auth blocks below.

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

Hmm, is this true for all API providers for SUI? Still a good note though.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

Yes we use GRPC for all providers for SUI. As for quicknode and port 9000, I'll drop this, I've experimented on this without 9000 port and worked fine, Quicknode handles this based on content type I guess.

name = "x-token"
token = { val = "YOUR_QUICKNODE_API_KEY" }

# ─── Mainnet variant ─────────────────────────────────────────────────────────

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.

Having separate sections is much better, thanks!

@haiyuechen-nearone haiyuechen-nearone 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.

📖

@netrome netrome left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

Thanks for updating!

@anodar
anodar added this pull request to the merge queue Aug 7, 2026
Merged via the queue into main with commit d45bd9b Aug 7, 2026
15 checks passed
@anodar
anodar deleted the 4023-document-expected-operator-foreign-chain-rpc-configurations branch August 7, 2026 18:20
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.

Document expected operator foreign chain RPC configurations

4 participants