partyId on the ledger — entirely from a React app.
How it works
1
Connect with Para
User authenticates through ParaModal and gets an embedded Solana wallet.
2
Register the public key with Canton
Server sends the Solana public key to Canton’s
generateExternalParty, which returns a multiHash challenge.3
Sign the challenge with Para
Client signs the
multiHash with useSignMessage.4
Allocate the party
Server submits the signature to Canton’s
allocateExternalParty, which returns a partyId.Prerequisites
- A Para API key from the Para Developer Portal
- Access to a Canton ledger and validator — either a hosted deployment or a local Splice LocalNet stack via docker-compose
- Node.js 18+ with Next.js (for the server-side Canton SDK calls)
- Basic familiarity with React and TypeScript
Installation
@canton-network/wallet-sdk) must run on the server. Using server-only ensures it never bundles into the browser.
Project structure
The Canton SDK holds credentials for your validator. Keep it in Next.js API routes so those credentials never reach the client.Setup
1. Configure the Para Provider
Set upParaProvider with embedded-wallet signups enabled. Para automatically provisions a Solana (Ed25519) wallet for each user, which is what Canton needs.
No
externalWalletConfig is set — Canton external parties are backed by Para’s own MPC-managed Solana key, not a user-supplied wallet like Phantom or MetaMask.2. Initialize the Canton SDK (server-only)
Createsrc/lib/canton.ts. This mirrors Canton’s own localNetAuthDefault pattern and is memoized so the SDK connects once per server process.
For production Canton deployments, replace
localNetAuthDefault with your validator’s authentication method (typically OAuth/JWT). Update VALIDATOR_AUDIENCE to match your validator’s expected audience.3. Create the API routes
/api/canton/generate — decodes the Solana address and calls Canton to prepare the external party challenge.
/api/canton/allocate — submits the Para-produced Ed25519 signature to finalize the party.
4. Build the onboarding hook
useCantonOnboarding does three things on the client:
- Makes sure the user’s Para Solana wallet is the active one (embedded accounts default to EVM).
- Fetches the Canton challenge, signs it with
useSignMessage, and submits the signature.
useSignMessage goes straight to Para’s MPC signMessage endpoint, so there’s no Solana RPC client to configure.
5. Wire up the UI
Environment variables
localNetAuthDefault for the appropriate auth factory, and set VALIDATOR_AUDIENCE to whatever your validator expects.
Complete example
A fully working Next.js app with this flow, including styled UI and error handling, is available in the Para Examples Hub:Canton External Party Example
Next.js + ParaModal + Canton Network — generate, sign, and allocate an external party on the Canton ledger
Related walkthroughs
Solana Transfers
Intermediate · 25 min · Send SOL with Web3.js, Signers v2, and Anchor
Ethereum Transfers
Intermediate · 20 min · Send ETH with Ethers and Viem
EIP-712 Typed Data Signing
Intermediate · 20 min · Structured data signing