alice.opq.eth-style names to CSAP meta-addresses on both
chains. A MetaMask sender resolves through the canonical OpaqueNameRegistry, an
ENSIP-10 wildcard resolver on Ethereum. A Phantom
sender resolves the same name from a read-only mirror PDA on Solana: one account fetch,
no Ethereum RPC. The mirror is written exclusively from Wormhole VAAs emitted by the
canonical registry. The full protocol is specified in
ONS.md.
On testnet the parent name in force is opqtest.eth (Sepolia); production opq.eth
is deferred until mainnet. The parent name, registry address, and mirror program ship in
@opaquecash/deployments (see Deployments).
ONS names resolve on Ethereum and Solana today. A Starknet mirror (an L1-to-L2 mirror
alongside the Solana one) is on the roadmap and not yet live.
How a name resolves
resolveRecipient (and therefore sendStealthPayment) accepts every name form
directly. Four paths exist, per
ONS.md section 7:
Every path validates that both 33-byte halves of the result are valid compressed
secp256k1 points before returning.
Step 1: Resolve a name
sdk/examples/ons-resolve.ts resolves a name through both paths
and asserts they return the same meta-address.
Step 2: Register a name on Ethereum
Registration on the canonical registry is first-come-first-served and immediately authoritative.registerOpaqueName submits with the configured Ethereum signer and
registers the wallet’s own meta-address halves:
sync(label) to re-publish the mirror payload.
Step 3: Claim a name from Solana
A Solana-only user claims without ever touching Ethereum. The claim is provisional:Use an existing .eth name
You do not need an ONS name if you already own an ENS name. Publish your meta-address as acom.opaque.meta text record
(ENSIP-5 reverse-DNS key form, defined in
CSAP.md section 2.9) and every
Opaque client resolves it.
The record value is your meta-address in the CSAP serialisation (viewing half
first), optionally prefixed with st:opq: for self-description. The SDK returns
exactly the right value:
Option A: ENS Manager app
- Open your name at app.ens.domains with the wallet that owns it.
- Go to the Records tab and choose Edit Records.
- Add a Text record with key
com.opaque.metaand the value above. - Confirm the transaction.
Option B: programmatic (viem)
Text records live on the name’s resolver. Look the resolver up, then callsetText
with the wallet that owns or manages the name (see the
ENS docs on text records):
Verify
*.eth path needs an ENS-capable client in the Opaque config
(ens: { client } with a mainnet or Sepolia viem PublicClient); see
OpaqueClient configuration.
If you also hold an ERC-6538 registry entry for the address the name points to, the
on-chain registry stays authoritative on conflict (CSAP section 2.9). Keep the text
record and the registry entry in sync after key rotations.
Use an existing .sol name
SNS (Solana Name Service) domains publish the same value in a Records V2 TXT record. Thest:opq: prefix makes the value self-describing, so it coexists with
other TXT uses. See the SNS developer docs and
@bonfida/spl-name-service
for the records API.
Write the record
Verify
.sol path uses the bundled Records V2 TXT reader over the solana connection.
Inject sns: { getRecord } to read from a custom source; see
OpaqueClient configuration.
Reference
- Protocol: ONS.md (payload
formats, claim flow, reconciliation states) and
CSAP.md section 2.9 (the
com.opaque.metarecord convention). - Addresses: Deployments lists the testnet registry and the
ons-mirror/ons-registrationprograms. - API: Stealth API covers
resolveOpaqueMetaAddress,registerOpaqueName,claimOpaqueName,getOpaqueNameStatus, andreconcileOpaqueName.