@provablehq/aleo-bridge-sdk 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -0
- package/README.md +390 -0
- package/dist/agent/index.d.ts +23 -0
- package/dist/agent/index.js +7 -0
- package/dist/agent/index.js.map +1 -0
- package/dist/chunk-NTWXJE7R.js +93 -0
- package/dist/chunk-NTWXJE7R.js.map +1 -0
- package/dist/chunk-OU6GVGG7.js +606 -0
- package/dist/chunk-OU6GVGG7.js.map +1 -0
- package/dist/createBridgeClient-DzmEyXfG.d.ts +1058 -0
- package/dist/index.d.ts +739 -0
- package/dist/index.js +3882 -0
- package/dist/index.js.map +1 -0
- package/dist/mcp/index.d.ts +28 -0
- package/dist/mcp/index.js +13 -0
- package/dist/mcp/index.js.map +1 -0
- package/dist/solana/index.d.ts +113 -0
- package/dist/solana/index.js +15 -0
- package/dist/solana/index.js.map +1 -0
- package/dist/solana-D5Qr6SLa.d.ts +725 -0
- package/package.json +74 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/errors/bridgeErrors.ts","../src/utils/xreserve.ts","../src/solana/igp.ts","../src/solana/kit.ts","../src/solana/transferRemote.ts","../src/solana/rpc.ts","../src/connections/solana.ts"],"sourcesContent":["/**\n * Represents protocol bridge configuration and planning failures.\n *\n * @example\n * try {\n * await bridge.quote(params)\n * } catch (error) {\n * if (error instanceof BridgeError) console.error(error.message)\n * }\n */\nexport class BridgeError extends Error {\n constructor(message: string, options?: ErrorOptions) {\n super(message, options)\n this.name = 'BridgeError'\n }\n}\n","import {\n encodeAbiParameters,\n getAddress,\n hexToBytes,\n isAddress,\n isHex,\n keccak256,\n padHex,\n toHex,\n type Address,\n type Hash,\n type Hex,\n} from 'viem'\nimport { BridgeError } from '../errors/bridgeErrors.js'\nimport type { AleoMintMode, BridgeEnvironment } from '../types/protocol.js'\n\nconst HOOK_DATA_BYTES = 65\nconst BECH32_ALPHABET = 'qpzry9x8gf2tvdw0s3jn54khce6mua7l'\n\nfunction bech32Polymod(values: readonly number[]): number {\n const generators = [0x3b6a57b2, 0x26508e6d, 0x1ea119fa, 0x3d4233dd, 0x2a1462b3]\n let checksum = 1\n for (const value of values) {\n const top = checksum >>> 25\n checksum = ((checksum & 0x1ffffff) << 5) ^ value\n for (let index = 0; index < 5; index++) if ((top >>> index) & 1) checksum ^= generators[index]!\n }\n return checksum >>> 0\n}\n\nfunction decodeAleoBech32m(address: string): Uint8Array {\n const separator = address.lastIndexOf('1')\n const prefix = address.slice(0, separator)\n const encoded = address.slice(separator + 1)\n const words = [...encoded].map((character) => BECH32_ALPHABET.indexOf(character))\n if (prefix !== 'aleo' || separator < 1 || words.some((word) => word < 0)) throw new Error('invalid encoding')\n const expanded = [...prefix].map((character) => character.charCodeAt(0) >>> 5)\n .concat([0], [...prefix].map((character) => character.charCodeAt(0) & 31), words)\n if (bech32Polymod(expanded) !== 0x2bc830a3) throw new Error('invalid checksum')\n const payload = words.slice(0, -6)\n const bytes: number[] = []\n let accumulator = 0\n let bits = 0\n for (const word of payload) {\n accumulator = (accumulator << 5) | word\n bits += 5\n while (bits >= 8) {\n bits -= 8\n bytes.push((accumulator >>> bits) & 0xff)\n }\n }\n if (bits >= 5 || ((accumulator << (8 - bits)) & 0xff) !== 0) throw new Error('invalid padding')\n return Uint8Array.from(bytes)\n}\n\n/**\n * Decodes a checksummed Aleo bech32m address into xReserve bytes32 form.\n *\n * Validates the supplied prefix, length, checksum, padding, and payload width\n * without contacting Aleo or Circle.\n *\n * @param address Aleo account address to encode.\n * @returns Exactly 32 decoded bytes as prefixed hexadecimal.\n * @throws BridgeError When the address has invalid bech32m structure.\n *\n * @example\n * const recipient = aleoAddressToBytes32('aleo1…')\n */\nexport function aleoAddressToBytes32(address: string): Hex {\n try {\n if (!address.startsWith('aleo1') || address.length !== 63) throw new Error('invalid prefix or length')\n const bytes = decodeAleoBech32m(address)\n if (bytes.length !== 32) throw new Error('invalid payload')\n return toHex(bytes)\n } catch (cause) {\n throw new BridgeError(`Invalid Aleo recipient address: ${address}`, { cause })\n }\n}\n\n/**\n * Restores the Aleo account address carried in a bridge protocol's bytes32 recipient field.\n *\n * Call this when reconstructing a transfer from Solana instructions or EVM\n * events, where the destination address is stored without its human-readable\n * prefix and checksum.\n *\n * @param recipient Exactly 32 Aleo address bytes encoded as prefixed hexadecimal.\n * @returns The canonical checksummed `aleo1…` account address.\n * @throws BridgeError When the recipient is not exactly 32 bytes.\n */\nexport function bytes32ToAleoAddress(recipient: Hex): string {\n if (!/^0x[0-9a-fA-F]{64}$/.test(recipient)) {\n throw new BridgeError(`Invalid 32-byte Aleo recipient: ${recipient}`)\n }\n const prefix = 'aleo'\n const words: number[] = []\n let accumulator = 0\n let bits = 0\n for (const byte of hexToBytes(recipient)) {\n accumulator = (accumulator << 8) | byte\n bits += 8\n while (bits >= 5) {\n bits -= 5\n words.push((accumulator >>> bits) & 31)\n }\n }\n if (bits > 0) words.push((accumulator << (5 - bits)) & 31)\n\n const expanded = [...prefix].map((character) => character.charCodeAt(0) >>> 5)\n .concat([0], [...prefix].map((character) => character.charCodeAt(0) & 31))\n const checksum = bech32Polymod([...expanded, ...words, 0, 0, 0, 0, 0, 0]) ^ 0x2bc830a3\n for (let index = 0; index < 6; index++) {\n words.push((checksum >>> (5 * (5 - index))) & 31)\n }\n return `${prefix}1${words.map((word) => BECH32_ALPHABET[word]).join('')}`\n}\n\nasync function loadAleoSdk(environment: BridgeEnvironment) {\n const moduleName = '@provablehq/sdk/dynamic.js'\n try {\n const sdk = await import(moduleName) as { loadNetwork: (network: BridgeEnvironment) => Promise<any> }\n return sdk.loadNetwork(environment)\n } catch (cause) {\n throw new BridgeError('Private xReserve mints require the optional @provablehq/sdk package', { cause })\n }\n}\n\n/**\n * Derives the Aleo account address owned by a deployed program id.\n *\n * Lazily loads the optional Aleo WASM SDK but performs no network access.\n *\n * @param programId Deployed Aleo program id whose account receives funds.\n * @param environment Consensus environment used for address derivation.\n * @returns The program-owned `aleo1…` account address.\n * @throws BridgeError When the optional SDK is unavailable or derivation fails.\n *\n * @example\n * const wrapper = await aleoProgramAddress('shielded_usdcx_wrapper.aleo', 'mainnet')\n */\nexport async function aleoProgramAddress(programId: string, environment: BridgeEnvironment): Promise<string> {\n const sdk = await loadAleoSdk(environment)\n return sdk.Address.fromProgramId(programId).to_string()\n}\n\n/**\n * Builds the fixed 65-byte xReserve hook for public, record, or wrapper-private minting.\n *\n * Public and record hooks use only the supplied values. Private hooks lazily\n * load Aleo WASM to commit the intended recipient with BHP256 and the selected\n * secret nonce. No chain or bridge provider is contacted.\n *\n * @param mode Destination mint transition selected by the caller.\n * @param recipient Intended Aleo recipient committed by private mode.\n * @param environment Consensus environment used by private commitment derivation.\n * @param secretNonce Aleo scalar literal used by the private commitment. Defaults to `0scalar`.\n * @returns A 65-byte hook whose first byte is 0, 1, or 2.\n * @throws BridgeError When private derivation lacks the optional SDK or the secret nonce is not a valid Aleo scalar.\n *\n * @example\n * const hook = await buildXReserveHookData('record', recipient, 'testnet')\n */\nexport async function buildXReserveHookData(\n mode: AleoMintMode,\n recipient: string,\n environment: BridgeEnvironment,\n secretNonce = '0scalar',\n): Promise<Hex> {\n const bytes = new Uint8Array(HOOK_DATA_BYTES)\n // Byte 0 selects the Aleo delivery transition. The remaining 64 bytes are\n // zero for provider-managed public/record mints and carry the private\n // recipient commitment in bytes 1..32 for wrapper-managed private minting.\n bytes[0] = mode === 'public' ? 0 : mode === 'record' ? 1 : 2\n if (mode === 'private') {\n const sdk = await loadAleoSdk(environment)\n const bits = sdk.Plaintext.fromString(recipient).toBitsLe()\n let scalar\n try {\n scalar = sdk.Scalar.fromString(secretNonce)\n } catch (cause) {\n throw new BridgeError(`Invalid private mint secret nonce: ${secretNonce}`, { cause })\n }\n // BHP256 binds the intended Aleo address to the secret nonce. Revealing the\n // same pair later proves who may complete the private destination mint.\n const commitment = new sdk.BHP256().commit(bits, scalar).toBytesLe()\n if (commitment.length !== 32) throw new BridgeError('Private mint commitment must contain 32 bytes')\n bytes.set(commitment, 1)\n }\n return toHex(bytes)\n}\n\n/**\n * Derives the Circle deposit nonce from source domain, transaction hash, and log index.\n *\n * Follows Circle's ABI-padded nonce preimage exactly without contacting Circle\n * or either chain.\n *\n * @param sourceDomain Circle domain of the source xReserve contract.\n * @param transactionHash Confirmed deposit transaction hash.\n * @param logIndex Zero-based `DepositedToRemote` receipt log index.\n * @returns The Keccak-256 deposit nonce.\n *\n * @example\n * const nonce = calculateXReserveDepositNonce(0, txHash, 3)\n */\nexport function calculateXReserveDepositNonce(sourceDomain: number, transactionHash: Hash, logIndex: number): Hash {\n // ABI encoding fixes domain and log index at 32 bytes each. Concatenate those\n // encodings with the 32-byte transaction hash before Keccak-256.\n const domain = encodeAbiParameters([{ type: 'uint32' }], [sourceDomain])\n const index = encodeAbiParameters([{ type: 'uint256' }], [BigInt(logIndex)])\n return keccak256(`0x${domain.slice(2)}${transactionHash.slice(2)}${index.slice(2)}`)\n}\n\nfunction uintBytes(value: bigint, bytes: number): Uint8Array {\n if (value < 0n || value >= 1n << BigInt(bytes * 8)) throw new BridgeError(`Unsigned value does not fit in ${bytes} bytes`)\n return hexToBytes(toHex(value, { size: bytes }))\n}\n\n/**\n * Builds the canonical 305-byte Circle xReserve v2 deposit payload.\n *\n * Rejects fields with invalid wire widths before constructing the payload. It\n * does not contact Circle or either chain.\n *\n * @param params Event-derived deposit values and reviewed route identifiers.\n * @returns The exact payload submitted to Circle's attester.\n * @throws BridgeError When a value is invalid or exceeds its wire width.\n *\n * @example\n * const payload = buildXReserveDepositPayload(fields)\n */\nexport function buildXReserveDepositPayload(params: {\n amount: bigint\n remoteDomain: number\n remoteToken: Hex\n remoteRecipient: Hex\n localToken: Address\n depositor: Address\n maxFee: bigint\n nonce: Hash\n hookData: Hex\n}): Hex {\n if (!isHex(params.remoteToken, { strict: true }) || hexToBytes(params.remoteToken).length !== 32) throw new BridgeError('remoteToken must contain 32 bytes')\n if (!isHex(params.remoteRecipient, { strict: true }) || hexToBytes(params.remoteRecipient).length !== 32) throw new BridgeError('remoteRecipient must contain 32 bytes')\n if (!isHex(params.hookData, { strict: true }) || hexToBytes(params.hookData).length !== HOOK_DATA_BYTES) throw new BridgeError('hookData must contain 65 bytes')\n if (!isAddress(params.localToken) || !isAddress(params.depositor)) throw new BridgeError('Payload EVM address is invalid')\n // Circle's signed message is a fixed 305-byte binary layout. Keep explicit\n // offsets so a port can reproduce the wire format without ABI assumptions:\n // header[0..8), amount[8..40), domain[40..44), remote token[44..76),\n // recipient[76..108), local token[108..140), depositor[140..172),\n // max fee[172..204), nonce[204..236), hook length[236..240), hook[240..305).\n const payload = new Uint8Array(305)\n payload.set([0x5a, 0x2e, 0x0a, 0xcd, 0, 0, 0, 1], 0)\n payload.set(uintBytes(params.amount, 32), 8)\n payload.set(uintBytes(BigInt(params.remoteDomain), 4), 40)\n payload.set(hexToBytes(params.remoteToken), 44)\n payload.set(hexToBytes(params.remoteRecipient), 76)\n payload.set(hexToBytes(padHex(getAddress(params.localToken), { size: 32 })), 108)\n payload.set(hexToBytes(padHex(getAddress(params.depositor), { size: 32 })), 140)\n payload.set(uintBytes(params.maxFee, 32), 172)\n payload.set(hexToBytes(params.nonce), 204)\n payload.set(uintBytes(BigInt(HOOK_DATA_BYTES), 4), 236)\n payload.set(hexToBytes(params.hookData), 240)\n return toHex(payload)\n}\n\n/**\n * Hashes a canonical xReserve deposit payload for Circle attestation lookup.\n *\n * Computes Keccak-256 from the supplied payload without contacting Circle.\n *\n * @param payload Canonical xReserve deposit bytes.\n * @returns The 32-byte Circle message hash.\n *\n * @example\n * const messageHash = calculateXReserveMessageHash(payload)\n */\nexport function calculateXReserveMessageHash(payload: Hex): Hash {\n return keccak256(payload)\n}\n\n/**\n * Reads the deposit nonce from Circle's fixed-width xReserve payload.\n *\n * Applications can use the nonce to verify Aleo delivery even when older saved\n * progress retained the signed payload but omitted the nonce as a separate field.\n * The payload is decoded in memory and no network or wallet is contacted.\n *\n * @param payload Canonical 305-byte xReserve deposit payload returned by Circle.\n * @returns The 32-byte deposit nonce used by the Aleo bridge nullifier mapping.\n * @throws BridgeError When the payload has the wrong header, width, or hook length.\n * @example const nonce = xReserveDepositNonceFromPayload(attestation.payload)\n */\nexport function xReserveDepositNonceFromPayload(payload: Hex): Hash {\n if (!isHex(payload, { strict: true })) throw new BridgeError('xReserve payload must be prefixed hexadecimal')\n const bytes = hexToBytes(payload)\n if (bytes.length !== 305\n || toHex(bytes.slice(0, 8)) !== '0x5a2e0acd00000001'\n || toHex(bytes.slice(236, 240)) !== '0x00000041') {\n throw new BridgeError('xReserve payload has an invalid deposit layout')\n }\n return toHex(bytes.slice(204, 236))\n}\n\n/**\n * Formats fixed-width hexadecimal bytes as an Aleo `[u8; N]` literal.\n *\n * Validates the exact byte width before formatting inputs for a wallet. It does\n * not contact Aleo or prompt the wallet.\n *\n * @param value Prefixed hexadecimal bytes to format.\n * @param expectedBytes Required array width from the target Aleo function.\n * @returns An Aleo array literal containing decimal `u8` values.\n * @throws BridgeError When the input is malformed or has the wrong width.\n *\n * @example\n * const hashInput = xReserveHexToAleoBytes(messageHash, 32)\n */\nexport function xReserveHexToAleoBytes(value: Hex, expectedBytes: number): string {\n if (!isHex(value, { strict: true })) throw new BridgeError('Aleo byte-array input must be prefixed hexadecimal')\n const bytes = hexToBytes(value)\n if (bytes.length !== expectedBytes) throw new BridgeError(`Aleo byte-array input must contain ${expectedBytes} bytes`)\n return `[${[...bytes].map((byte) => `${byte}u8`).join(',')}]`\n}\n\n/**\n * Encodes an Ethereum address as the 32-byte recipient required by xReserve burns.\n *\n * Preserves the 20 address bytes and adds twelve leading zero bytes without\n * contacting Ethereum or Circle.\n *\n * @param address Checksummed or lowercase Ethereum address selected by the caller.\n * @returns The address left-padded to exactly 32 bytes.\n * @throws BridgeError When the address is malformed.\n *\n * @example\n * const recipient = evmAddressToXReserveBytes32('0x0000000000000000000000000000000000000001')\n */\nexport function evmAddressToXReserveBytes32(address: string): Hex {\n if (!isAddress(address)) throw new BridgeError(`Invalid Ethereum recipient address: ${address}`)\n return padHex(getAddress(address), { size: 32 })\n}\n","import { BridgeError } from '../errors/bridgeErrors.js'\n\n// SEALEVEL_NOTES.md §4: fixed-point scale for `token_exchange_rate` — a rate\n// of 1.0 is stored on-chain as 10^19.\nconst TOKEN_EXCHANGE_RATE_SCALE = 10n ** 19n\n\n// SEALEVEL_NOTES.md §4: SOL's native decimal width, used to rescale the\n// oracle's origin-chain-denominated cost into lamports.\nconst SOL_DECIMALS = 9\n\n// SEALEVEL_NOTES.md §4: fixed byte offsets preceding the gas-oracle table —\n// `AccountData<DiscriminatorPrefixed<Igp>>`'s `[1B initialized][8B \"IGP_____\"\n// discriminator][1B bump_seed][32B salt]` header, followed by `Igp`'s own\n// `[1B owner Option tag (+32B when Some)][32B beneficiary][4B oracle count]`.\nconst INITIALIZED_BYTES = 1\nconst DISCRIMINATOR_BYTES = 8\nconst BUMP_SEED_BYTES = 1\nconst SALT_BYTES = 32\nconst PUBKEY_BYTES = 32\nconst ORACLE_COUNT_BYTES = 4\n\n// SEALEVEL_NOTES.md §4: one `gas_oracles` entry — `GAS_ORACLE_ENTRY_SIZE`\n// (accounts.rs) — `[4B domain][1B GasOracle tag][16B token_exchange_rate]\n// [16B gas_price][1B token_decimals]`.\nconst GAS_ORACLE_ENTRY_BYTES = 38\nconst DOMAIN_BYTES = 4\nconst GAS_ORACLE_TAG_BYTES = 1\nconst EXCHANGE_RATE_BYTES = 16\nconst GAS_PRICE_BYTES = 16\n\nfunction readUint128LE(view: DataView, offset: number): bigint {\n let value = 0n\n for (let index = EXCHANGE_RATE_BYTES - 1; index >= 0; index--) {\n value = (value << 8n) | BigInt(view.getUint8(offset + index))\n }\n return value\n}\n\n/**\n * Computes the lamport gas payment a Sealevel interchain gas paymaster (IGP)\n * quotes for delivering a message to a given destination domain.\n *\n * Decodes the supplied IGP account's gas-oracle table and applies the\n * paymaster's `compute_gas_fee` formula (SEALEVEL_NOTES.md §4) without\n * contacting Solana. `igpAccountData` must be the terminal, quoted `Igp`\n * account — the one an `OverheadIgp` wrapper's own `inner` field points at,\n * not the `OverheadIgp` wrapper account itself — and `gasAmount` must be the\n * warp token's own `destination_gas` value for the domain, not derived from\n * the message.\n *\n * @param params.igpAccountData Raw account data of the terminal Sealevel `Igp` account.\n * @param params.destinationDomain Hyperlane domain the transfer is bound for.\n * @param params.gasAmount Destination gas units to quote, as reported by the warp token's `destination_gas` configuration.\n * @returns The gas payment required, in lamports.\n * @throws BridgeError When `igpAccountData` has no gas-oracle entry for `destinationDomain`.\n *\n * @example\n * const lamports = quoteIgpGasPayment({\n * igpAccountData: await rpc.getAccountData(route.igpAccount) ?? new Uint8Array(),\n * destinationDomain: route.destinationDomain,\n * gasAmount: BigInt(route.destinationGasAmount),\n * })\n */\nexport function quoteIgpGasPayment(params: {\n igpAccountData: Uint8Array\n destinationDomain: number\n gasAmount: bigint\n}): bigint {\n const { igpAccountData } = params\n const view = new DataView(igpAccountData.buffer, igpAccountData.byteOffset, igpAccountData.byteLength)\n\n const requireBytes = (offset: number, length: number): void => {\n if (offset < 0 || length < 0 || offset + length > view.byteLength) {\n throw new BridgeError('malformed Sealevel IGP account data: declared layout exceeds the supplied bytes')\n }\n }\n\n let offset = INITIALIZED_BYTES + DISCRIMINATOR_BYTES + BUMP_SEED_BYTES + SALT_BYTES\n requireBytes(offset, 1)\n const ownerOptionTag = view.getUint8(offset)\n offset += 1\n if (ownerOptionTag !== 0 && ownerOptionTag !== 1) {\n throw new BridgeError(`malformed Sealevel IGP account data: unsupported owner option tag ${ownerOptionTag}`)\n }\n if (ownerOptionTag === 1) {\n requireBytes(offset, PUBKEY_BYTES)\n offset += PUBKEY_BYTES\n }\n requireBytes(offset, PUBKEY_BYTES + ORACLE_COUNT_BYTES)\n offset += PUBKEY_BYTES // beneficiary\n\n const oracleCount = view.getUint32(offset, true)\n offset += ORACLE_COUNT_BYTES\n\n for (let index = 0; index < oracleCount; index++) {\n const entryStart = offset\n requireBytes(entryStart, GAS_ORACLE_ENTRY_BYTES)\n const domain = view.getUint32(entryStart, true)\n if (domain === params.destinationDomain) {\n // SEALEVEL_NOTES.md §4: `RemoteGasData` (tag 0) is the only `GasOracle`\n // variant defined today. Assert it rather than silently decoding a\n // future variant's bytes as if they were `RemoteGasData`'s.\n const tagOffset = entryStart + DOMAIN_BYTES\n const gasOracleTag = view.getUint8(tagOffset)\n if (gasOracleTag !== 0) {\n throw new BridgeError(\n `Sealevel IGP account has an unexpected GasOracle variant tag ${gasOracleTag} for domain `\n + `${params.destinationDomain}; only variant 0 (RemoteGasData) is decoded`,\n )\n }\n\n const exchangeRateOffset = tagOffset + GAS_ORACLE_TAG_BYTES\n const gasPriceOffset = exchangeRateOffset + EXCHANGE_RATE_BYTES\n const decimalsOffset = gasPriceOffset + GAS_PRICE_BYTES\n\n const tokenExchangeRate = readUint128LE(view, exchangeRateOffset)\n const gasPrice = readUint128LE(view, gasPriceOffset)\n const tokenDecimals = view.getUint8(decimalsOffset)\n\n // SEALEVEL_NOTES.md §4 `compute_gas_fee` / `convert_decimals`.\n const destinationCost = params.gasAmount * gasPrice\n const originCost = (destinationCost * tokenExchangeRate) / TOKEN_EXCHANGE_RATE_SCALE\n return SOL_DECIMALS >= tokenDecimals\n ? originCost * 10n ** BigInt(SOL_DECIMALS - tokenDecimals)\n : originCost / 10n ** BigInt(tokenDecimals - SOL_DECIMALS)\n }\n offset += GAS_ORACLE_ENTRY_BYTES\n }\n\n throw new BridgeError(\n `Sealevel IGP account has no gas-oracle entry for destination domain ${params.destinationDomain}`,\n )\n}\n","import { BridgeError } from '../errors/bridgeErrors.js'\n\nlet kitModulePromise: Promise<typeof import('@solana/kit')> | undefined\n\n/**\n * Lazily imports the optional `@solana/kit` peer dependency.\n *\n * This is the only module in the package permitted to import `@solana/kit`\n * directly, so applications that never use Solana do not load the optional\n * dependency. The import is performed at most once per process and does not\n * contact a chain or wallet.\n *\n * @returns The `@solana/kit` module namespace once dynamic import resolves.\n * @throws BridgeError When `@solana/kit` cannot be resolved, naming the\n * install command and wrapping the original module-resolution error as\n * `cause`.\n *\n * @example\n * const kit = await loadKit()\n * const signer = await kit.createKeyPairSignerFromBytes(secretKeyBytes)\n */\nexport async function loadKit(): Promise<typeof import('@solana/kit')> {\n kitModulePromise ??= import('@solana/kit')\n try {\n return await kitModulePromise\n } catch (cause) {\n throw new BridgeError(\n 'Solana support requires the optional peer dependency @solana/kit; install it with: pnpm add @solana/kit',\n { cause },\n )\n }\n}\n","import { hexToBytes } from 'viem'\nimport { BridgeError } from '../errors/bridgeErrors.js'\nimport type { SolanaHyperlaneRouteMetadata } from '../types/solana.js'\nimport { aleoAddressToBytes32 } from '../utils/xreserve.js'\nimport { loadKit } from './kit.js'\n\n// SEALEVEL_NOTES.md §1: every Sealevel Hyperlane program instruction is\n// prefixed with this fixed 8-byte discriminator, hardcoded rather than\n// derived (mirrors the TS SDK's `Buffer.from([1, 1, 1, 1, 1, 1, 1, 1])`).\nconst PROGRAM_INSTRUCTION_DISCRIMINATOR = Uint8Array.of(1, 1, 1, 1, 1, 1, 1, 1)\n\n// SEALEVEL_NOTES.md §1: Borsh enum variant tag for `Instruction::TransferRemote`\n// (declaration order 1, 0-based: `Init=0`, `TransferRemote=1`, …).\nconst TRANSFER_REMOTE_VARIANT_TAG = 1\n\n// SEALEVEL_NOTES.md §2, rows 0 and 14: the native System program id appears\n// twice in the account list — once for the Mailbox's rent/lamport transfer,\n// once again for the native-collateral plugin's `transfer_in` CPI.\nconst SYSTEM_PROGRAM_ADDRESS = '11111111111111111111111111111111'\n\n// SEALEVEL_NOTES.md §3: PDA seeds are UTF-8 string segments (auto-encoded by\n// `@solana/kit`'s `getProgramDerivedAddress`) interleaved with the raw\n// 32-byte unique-message pubkey.\nconst DISPATCHED_MESSAGE_PDA_SEED_PREFIX = ['hyperlane', '-', 'dispatched_message', '-'] as const\nconst GAS_PAYMENT_PDA_SEED_PREFIX = ['hyperlane_igp', '-', 'gas_payment', '-'] as const\n\nconst INSTRUCTION_DATA_BYTES = 77 // SEALEVEL_NOTES.md §1: 8 + 1 + 4 + 32 + 32\nconst U256_BYTES = 32\n\n/**\n * Identifies one Solana account entry in a compiled instruction's account list.\n *\n * @property address Base58-encoded Solana account address.\n * @property signer Whether the transaction must carry this account's signature.\n * @property writable Whether the runtime may write to this account during the instruction.\n */\nexport type SolanaAccountMeta = {\n address: string\n signer: boolean\n writable: boolean\n}\n\n/**\n * Selects the route, parties, and amount for one Sealevel `TransferRemote` instruction.\n *\n * @property metadata Reviewed static accounts and domain for the Solana Hyperlane Warp Route.\n * @property senderAddress Base58 address of the wallet funding the transfer; signs and pays rent.\n * @property uniqueMessageAddress Base58 address of a fresh, caller-supplied signer that seeds the\n * dispatched-message and gas-payment program-derived addresses and proves transaction uniqueness.\n * @property recipientAleoAddress Aleo `aleo1…` address receiving the transfer on the destination chain.\n * @property amountLamports Amount to transfer, in lamports.\n */\nexport type BuildTransferRemoteParameters = {\n metadata: SolanaHyperlaneRouteMetadata\n senderAddress: string\n uniqueMessageAddress: string\n recipientAleoAddress: string\n amountLamports: bigint\n}\n\nfunction writeU32LE(bytes: Uint8Array, offset: number, value: number): void {\n bytes[offset] = value & 0xff\n bytes[offset + 1] = (value >>> 8) & 0xff\n bytes[offset + 2] = (value >>> 16) & 0xff\n bytes[offset + 3] = (value >>> 24) & 0xff\n}\n\nfunction writeU256LE(bytes: Uint8Array, offset: number, value: bigint): void {\n if (value < 0n || value >= 1n << BigInt(U256_BYTES * 8)) {\n throw new BridgeError(`amountLamports does not fit in a ${U256_BYTES}-byte unsigned integer`)\n }\n let remaining = value\n for (let index = 0; index < U256_BYTES; index++) {\n bytes[offset + index] = Number(remaining & 0xffn)\n remaining >>= 8n\n }\n}\n\n/**\n * Builds the Solana instruction that commits SOL to a Hyperlane transfer bound for Aleo.\n *\n * The result is unsigned and cannot move funds until the sender and unique\n * message account sign it and a client broadcasts it. Every program account is\n * supplied by reviewed route metadata or derived from the unique message key;\n * no network or wallet is contacted. The encoding is verified byte-for-byte\n * against `test/fixtures/sealevel-transfer-remote.json`.\n *\n * @param params Route metadata, transfer parties, and the lamport amount to move.\n * @returns The Warp Route program, ordered accounts, and raw 77-byte instruction data needed to assemble the transaction.\n * @throws BridgeError When `amountLamports` does not fit the instruction's 32-byte unsigned width,\n * or when `recipientAleoAddress` is not a valid Aleo address.\n *\n * @example\n * const instruction = await buildTransferRemoteInstruction({\n * metadata: route.solana,\n * senderAddress: await walletClient.getAddress(),\n * uniqueMessageAddress: uniqueSigner.address,\n * recipientAleoAddress: 'aleo1…',\n * amountLamports: 1_000_000_000n,\n * })\n */\nexport async function buildTransferRemoteInstruction(\n params: BuildTransferRemoteParameters,\n): Promise<{ programAddress: string; accounts: SolanaAccountMeta[]; data: Uint8Array }> {\n const { metadata } = params\n const kit = await loadKit()\n const addressEncoder = kit.getAddressEncoder()\n const uniqueMessageBytes = addressEncoder.encode(kit.address(params.uniqueMessageAddress))\n\n // SEALEVEL_NOTES.md §2 row 8, §3: dispatched-message PDA lives on the\n // Mailbox program, seeded by the unique-message pubkey.\n const [dispatchedMessagePda] = await kit.getProgramDerivedAddress({\n programAddress: kit.address(metadata.mailboxProgramAddress),\n seeds: [...DISPATCHED_MESSAGE_PDA_SEED_PREFIX, uniqueMessageBytes],\n })\n\n // SEALEVEL_NOTES.md §2 row 11, §3: gas-payment PDA lives on the IGP\n // program, seeded by the same unique-message pubkey (reused as the\n // \"unique gas payment\" key).\n const [gasPaymentPda] = await kit.getProgramDerivedAddress({\n programAddress: kit.address(metadata.igpProgramAddress),\n seeds: [...GAS_PAYMENT_PDA_SEED_PREFIX, uniqueMessageBytes],\n })\n\n // SEALEVEL_NOTES.md §1: [8B discriminator][1B enum tag][4B LE domain][32B recipient][32B LE amount].\n const data = new Uint8Array(INSTRUCTION_DATA_BYTES)\n data.set(PROGRAM_INSTRUCTION_DISCRIMINATOR, 0)\n data[8] = TRANSFER_REMOTE_VARIANT_TAG\n writeU32LE(data, 9, metadata.destinationDomain)\n data.set(hexToBytes(aleoAddressToBytes32(params.recipientAleoAddress)), 13)\n writeU256LE(data, 45, params.amountLamports)\n\n // SEALEVEL_NOTES.md §2: the ordered account table, interleaving\n // route-static metadata (read from the token's own on-chain\n // configuration in a live system) with the two per-transfer signers and\n // the two PDAs derived above. The sender compiles writable despite not\n // being a writable-flagged account elsewhere — Solana's compiler unions\n // writability across every instruction referencing an account, and the\n // native-collateral transfer CPI needs it writable (§2, closing note).\n const accounts: SolanaAccountMeta[] = [\n { address: SYSTEM_PROGRAM_ADDRESS, signer: false, writable: false }, // row 0\n { address: metadata.splNoopProgramAddress, signer: false, writable: false }, // row 1\n { address: metadata.tokenPda, signer: false, writable: false }, // row 2\n { address: metadata.mailboxProgramAddress, signer: false, writable: false }, // row 3\n { address: metadata.mailboxOutboxPda, signer: false, writable: true }, // row 4\n { address: metadata.dispatchAuthorityPda, signer: false, writable: false }, // row 5\n { address: params.senderAddress, signer: true, writable: true }, // row 6\n { address: params.uniqueMessageAddress, signer: true, writable: false }, // row 7\n { address: dispatchedMessagePda, signer: false, writable: true }, // row 8\n { address: metadata.igpProgramAddress, signer: false, writable: false }, // row 9\n { address: metadata.igpProgramDataPda, signer: false, writable: true }, // row 10\n { address: gasPaymentPda, signer: false, writable: true }, // row 11\n // row 12 (optional): only present when the route wraps its IGP in an\n // `OverheadIgp` — omitted entirely otherwise (SEALEVEL_NOTES.md §2 row\n // 12, \"optional slot\").\n ...(metadata.igpOverheadAccount\n ? [{ address: metadata.igpOverheadAccount, signer: false, writable: false }]\n : []),\n { address: metadata.igpAccount, signer: false, writable: true }, // row 13\n { address: SYSTEM_PROGRAM_ADDRESS, signer: false, writable: false }, // row 14\n { address: metadata.nativeCollateralPda, signer: false, writable: true }, // row 15\n ]\n\n return { programAddress: metadata.warpProgramAddress, accounts, data }\n}\n","import { BridgeError } from '../errors/bridgeErrors.js'\nimport type { SolanaRpcConfig } from '../types/solana.js'\n\n/**\n * Confirmation state Solana reports for a submitted transaction signature.\n *\n * `'failed'` is synthesized locally from a non-null `err` field on the\n * `getSignatureStatuses` result; Solana itself only ever reports a\n * `confirmationStatus`, never a failure status.\n */\ntype SolanaSignatureConfirmationStatus = 'processed' | 'confirmed' | 'finalized' | 'failed'\n\n/**\n * Reads live Solana chain state needed to prepare, submit, and confirm a\n * Hyperlane Warp Route transfer.\n *\n * Every method hits the configured Solana JSON-RPC endpoint over the network;\n * none of them sign or submit a transaction.\n *\n * @property getLatestBlockhash Reads the current blockhash and the block height it remains valid through.\n * @property getBlockHeight Reads the current block height used to detect transaction expiry.\n * @property isBlockhashValid Reports whether a recent blockhash remains valid at confirmed commitment.\n * @property getBalance Reads an account's lamport balance.\n * @property getAccountData Reads an account's raw data, or `null` when the account does not exist.\n * @property getFeeForMessage Reads the network fee for a compiled transaction message, in lamports.\n * @property getMinimumBalanceForRentExemption Reads the rent-exempt minimum for an account data length, in lamports.\n * @property getSignatureStatus Reads a submitted transaction's confirmation state, or `null` when the signature is unknown to the node.\n * @property getTransactionLogs Reads a confirmed transaction's program logs, or `null` when the transaction is not found.\n */\nexport type SolanaRpcClient = {\n getLatestBlockhash: () => Promise<{ blockhash: string; lastValidBlockHeight: bigint }>\n getBlockHeight: () => Promise<bigint>\n isBlockhashValid: (blockhash: string) => Promise<boolean>\n getBalance: (address: string) => Promise<bigint>\n getAccountData: (address: string) => Promise<Uint8Array | null>\n getFeeForMessage: (message: Uint8Array) => Promise<bigint>\n getMinimumBalanceForRentExemption: (dataLength: number) => Promise<bigint>\n getSignatureStatus: (signature: string) => Promise<SolanaSignatureConfirmationStatus | null>\n getTransactionLogs: (signature: string) => Promise<string[] | null>\n}\n\n/** Describes the result and error fields returned by a Solana JSON-RPC request. */\ntype JsonRpcResponse<T> = {\n result?: T\n error?: { code?: number; message?: string }\n}\n\n/** Describes the `{ context, value }` envelope Solana uses for most read results. */\ntype ContextualResult<T> = { value: T }\n\nfunction decodeBase64(value: string): Uint8Array {\n const binary = atob(value)\n const bytes = new Uint8Array(binary.length)\n for (let index = 0; index < binary.length; index++) {\n bytes[index] = binary.charCodeAt(index)\n }\n return bytes\n}\n\n/**\n * Creates the Solana network reader used to quote and follow Hyperlane transfers.\n *\n * Every method sends one JSON-RPC request through the supplied transport and\n * validates the response before returning it. No method requests a wallet\n * signature or submits a transaction.\n *\n * @param config Solana JSON-RPC endpoint and optional Fetch API replacement. The transport defaults to `globalThis.fetch`.\n * @returns Network reads for blockhashes, balances, fees, rent, accounts, signatures, and logs.\n *\n * @example\n * const rpc = createSolanaRpcClient({ url: 'https://api.mainnet-beta.solana.com' })\n * const { blockhash } = await rpc.getLatestBlockhash()\n */\nexport function createSolanaRpcClient(config: SolanaRpcConfig): SolanaRpcClient {\n async function call<T>(method: string, params: unknown[]): Promise<T> {\n // This is the single trust boundary for every Solana read: distinguish\n // transport failure, invalid JSON, JSON-RPC error, and a missing result so\n // operators can tell endpoint problems from transaction failure.\n const transport = config.transport ?? globalThis.fetch\n const response = await transport(config.url, {\n method: 'POST',\n headers: { 'content-type': 'application/json', 'cache-control': 'no-cache' },\n body: JSON.stringify({ jsonrpc: '2.0', id: 1, method, params }),\n cache: 'no-store',\n })\n if (!response.ok) {\n throw new BridgeError(`Solana RPC ${method} request failed with HTTP status ${response.status}`, {\n cause: { status: response.status },\n })\n }\n let rawBody: unknown\n try {\n rawBody = await response.json()\n } catch (error) {\n throw new BridgeError(`Solana RPC ${method} returned invalid JSON`, { cause: error })\n }\n if (!rawBody || typeof rawBody !== 'object') {\n throw new BridgeError(`Solana RPC ${method} returned an invalid JSON-RPC response`)\n }\n const body = rawBody as JsonRpcResponse<T>\n if (body.error) {\n throw new BridgeError(`Solana RPC ${method} returned a JSON-RPC error: ${body.error.message ?? 'unknown error'}`, {\n cause: body.error,\n })\n }\n if (!Object.prototype.hasOwnProperty.call(body, 'result') || body.result === undefined) {\n throw new BridgeError(`Solana RPC ${method} returned an invalid result envelope`)\n }\n return body.result as T\n }\n\n function integer(method: string, value: unknown): bigint {\n // Solana emits these quantities as JSON numbers. Convert only safe,\n // non-negative integers before later arithmetic switches to bigint.\n if (typeof value !== 'number' || !Number.isSafeInteger(value) || value < 0) {\n throw new BridgeError(`Solana RPC ${method} returned an invalid result`)\n }\n return BigInt(value)\n }\n\n function contextualValue<T>(method: string, result: unknown): T {\n if (!result || typeof result !== 'object' || !Object.prototype.hasOwnProperty.call(result, 'value')) {\n throw new BridgeError(`Solana RPC ${method} returned an invalid contextual result`)\n }\n return (result as ContextualResult<T>).value\n }\n\n return {\n async getLatestBlockhash() {\n const result = await call<unknown>(\n 'getLatestBlockhash',\n [{ commitment: 'confirmed' }],\n )\n const value = contextualValue<{ blockhash: string; lastValidBlockHeight: number }>('getLatestBlockhash', result)\n if (!value || typeof value.blockhash !== 'string' || !value.blockhash) {\n throw new BridgeError('Solana RPC getLatestBlockhash returned an invalid result')\n }\n return { blockhash: value.blockhash, lastValidBlockHeight: integer('getLatestBlockhash', value.lastValidBlockHeight) }\n },\n\n async getBlockHeight() {\n return integer('getBlockHeight', await call<unknown>('getBlockHeight', []))\n },\n\n async isBlockhashValid(blockhash) {\n const result = await call<unknown>('isBlockhashValid', [blockhash, { commitment: 'confirmed' }])\n const value = contextualValue<unknown>('isBlockhashValid', result)\n if (typeof value !== 'boolean') {\n throw new BridgeError('Solana RPC isBlockhashValid returned an invalid result')\n }\n return value\n },\n\n async getBalance(address) {\n const value = contextualValue<unknown>('getBalance', await call<unknown>('getBalance', [address]))\n return integer('getBalance', value)\n },\n\n async getFeeForMessage(message) {\n const base64 = btoa(String.fromCharCode(...message))\n const result = await call<unknown>('getFeeForMessage', [base64, { commitment: 'confirmed' }])\n return integer('getFeeForMessage', contextualValue('getFeeForMessage', result))\n },\n\n async getMinimumBalanceForRentExemption(dataLength) {\n if (!Number.isSafeInteger(dataLength) || dataLength < 0) {\n throw new BridgeError('Solana rent data length must be a non-negative integer')\n }\n return integer('getMinimumBalanceForRentExemption', await call<unknown>('getMinimumBalanceForRentExemption', [dataLength]))\n },\n\n async getAccountData(address) {\n const result = await call<unknown>('getAccountInfo', [\n address,\n { encoding: 'base64' },\n ])\n const value = contextualValue<{ data: [string, string] } | null>('getAccountInfo', result)\n if (!value) return null\n if (!Array.isArray(value.data) || typeof value.data[0] !== 'string' || value.data[1] !== 'base64') {\n throw new BridgeError('Solana RPC getAccountInfo returned invalid base64 account data')\n }\n try {\n return decodeBase64(value.data[0])\n } catch (error) {\n throw new BridgeError('Solana RPC getAccountInfo returned invalid base64 account data', { cause: error })\n }\n },\n\n async getSignatureStatus(signature) {\n // Search historical slots as well as the node's recent-status cache;\n // recovery may run long after the original process submitted the transfer.\n const result = await call<unknown>(\n 'getSignatureStatuses',\n [[signature], { searchTransactionHistory: true }],\n )\n const value = contextualValue<({ err: unknown; confirmationStatus?: string } | null)[]>('getSignatureStatuses', result)\n if (!Array.isArray(value) || value.length !== 1) {\n throw new BridgeError('Solana RPC getSignatureStatuses returned an invalid result')\n }\n const status = value[0]\n if (!status) return null\n if (typeof status !== 'object' || !Object.prototype.hasOwnProperty.call(status, 'err')) {\n throw new BridgeError('Solana RPC getSignatureStatuses returned an invalid status')\n }\n if (status.err) return 'failed'\n if (status.confirmationStatus === undefined) return null\n if (!['processed', 'confirmed', 'finalized'].includes(status.confirmationStatus)) {\n throw new BridgeError(`Solana RPC getSignatureStatuses returned unsupported confirmation status: ${status.confirmationStatus}`)\n }\n return status.confirmationStatus as SolanaSignatureConfirmationStatus\n },\n\n async getTransactionLogs(signature) {\n // Solana's JSON-RPC `getTransaction` defaults to `finalized` commitment\n // when none is given; a transaction that has only reached `confirmed`\n // then returns null even though it already landed, missing the\n // Hyperlane dispatch log. Request `confirmed` explicitly.\n const result = await call<{ meta: { logMessages: string[] | null } | null } | null>('getTransaction', [\n signature,\n { maxSupportedTransactionVersion: 0, commitment: 'confirmed' },\n ])\n if (result === null) return null\n if (!result || typeof result !== 'object' || !Object.prototype.hasOwnProperty.call(result, 'meta')) {\n throw new BridgeError('Solana RPC getTransaction returned an invalid result')\n }\n const meta = result.meta\n if (!meta || typeof meta !== 'object' || !Object.prototype.hasOwnProperty.call(meta, 'logMessages')) {\n throw new BridgeError('Solana RPC getTransaction returned invalid metadata')\n }\n const logs = meta.logMessages\n if (logs !== null && (!Array.isArray(logs) || logs.some((line) => typeof line !== 'string'))) {\n throw new BridgeError('Solana RPC getTransaction returned invalid logs')\n }\n return logs ?? null\n },\n }\n}\n","import { BridgeError } from '../errors/bridgeErrors.js'\nimport bs58 from 'bs58'\nimport { loadKit } from '../solana/kit.js'\nimport { createSolanaRpcClient, type SolanaRpcClient } from '../solana/rpc.js'\nimport type { SolanaRpcHttpTransport } from '../types/solana.js'\n\nconst SOLANA_SIGN_AND_SEND_TRANSACTION_FEATURE = 'solana:signAndSendTransaction'\n\n/** Provides Solana's public mainnet endpoint as the default for examples and low-volume reads. */\nexport const DEFAULT_SOLANA_RPC_URL = 'https://api.mainnet-beta.solana.com'\n\ntype SolanaSignAndSendTransactionFeature = {\n signAndSendTransaction: (input: {\n transaction: Uint8Array\n account: { address: string; publicKey: Uint8Array }\n chain: string\n }) => Promise<readonly { signature: Uint8Array }[]>\n}\n\n/**\n * Sends one Solana JSON-RPC method through an application transport.\n * @param method JSON-RPC method name.\n * @param params Positional JSON-RPC parameters.\n * @returns The decoded method result.\n */\nexport type SolanaRequest = (method: string, params: unknown[]) => Promise<unknown>\n\n/**\n * Configures Fetch API behavior for a Solana HTTP transport.\n * @property fetch Optional fetch-compatible JSON-RPC transport.\n */\nexport type SolanaHttpOptions = { fetch?: SolanaRpcHttpTransport | undefined }\n\n/** Stores an HTTP endpoint or custom JSON-RPC function without contacting Solana. */\nexport type SolanaTransport =\n | { type: 'http'; url: string; fetch?: SolanaRpcHttpTransport | undefined }\n | { type: 'custom'; request: SolanaRequest }\n\n/** Selects whether a Wallet Standard account or application-held key authorizes transactions. */\nexport type SolanaAccount =\n | {\n type: 'wallet'\n wallet: { features: Record<string, unknown> }\n account: { address: string; publicKey: Uint8Array }\n chain: string\n }\n | { type: 'local'; secretKeyBytes: Uint8Array }\n\n/**\n * Configures Solana network and optional wallet access for one named bridge chain.\n * @property transport Required public JSON-RPC transport.\n * @property account Optional Wallet Standard or local-key signing authority.\n */\nexport type SolanaClientConfig = {\n transport: SolanaTransport\n account?: SolanaAccount | undefined\n}\n\n/**\n * Exposes account-free Solana operations used by bridge actions.\n * @property sendTransaction Broadcasts a fully signed wire transaction.\n */\nexport type SolanaPublicClient = SolanaRpcClient & {\n sendTransaction: (signedTransaction: Uint8Array) => Promise<{ signature: string }>\n}\n\n/**\n * Exposes account-authorized Solana operations used by bridge actions.\n * @property getAddress Resolves the fee payer address.\n * @property sendTransaction Adds the fee-payer signature and broadcasts or delegates both operations to a wallet.\n */\nexport type SolanaWalletClient = {\n getAddress: () => Promise<string>\n sendTransaction: (wireTransaction: Uint8Array) => Promise<{ signature: string }>\n}\n\n/**\n * Holds materialized Solana public and wallet capabilities.\n * @property family Prevents this client from being used for an EVM or Aleo route stored under the wrong chain identifier.\n * @property publicClient Read and broadcast capability.\n * @property walletClient Optional signing capability.\n */\nexport type SolanaClient = {\n family: 'solana'\n publicClient: SolanaPublicClient\n walletClient?: SolanaWalletClient | undefined\n}\n\n/**\n * Defines the Solana JSON-RPC endpoint used when a bridge action reads or submits.\n *\n * Creating the transport does not contact the endpoint.\n *\n * @param url Solana JSON-RPC endpoint contacted by the resulting client.\n * @param options Optional Fetch API implementation. Defaults to `globalThis.fetch` when the client is created.\n * @returns Deferred HTTP configuration accepted by `createSolanaClient`.\n * @example const transport = solanaHttp('https://api.mainnet-beta.solana.com')\n */\nexport function solanaHttp(url: string, options: SolanaHttpOptions = {}): SolanaTransport {\n return { type: 'http', url, fetch: options.fetch }\n}\n\n/**\n * Defines Solana network access through an application-supplied JSON-RPC function.\n *\n * Creating the transport does not call the request function.\n *\n * @param request Function that sends JSON-RPC methods when a bridge action needs network access.\n * @returns Deferred custom transport configuration accepted by `createSolanaClient`.\n * @example const transport = solanaCustom((method, params) => rpc.request(method, params))\n */\nexport function solanaCustom(request: SolanaRequest): SolanaTransport {\n return { type: 'custom', request }\n}\n\n/**\n * Selects a Wallet Standard account to authorize Solana bridge transactions.\n *\n * The wallet retains custody of the account and controls signing and broadcast.\n * This helper does not connect to the wallet or request a signature.\n *\n * @param params Wallet, selected account, and Wallet Standard chain identifier used for later authorization.\n * @returns Deferred wallet configuration accepted by `createSolanaClient`.\n * @example const account = solanaWallet({ wallet, account: wallet.accounts[0], chain: 'solana:mainnet' })\n */\nexport function solanaWallet(params: Omit<Extract<SolanaAccount, { type: 'wallet' }>, 'type'>): SolanaAccount {\n return { type: 'wallet', ...params }\n}\n\n/**\n * Selects an application-held Solana keypair for unattended bridge transactions.\n *\n * The keypair signs on the caller's device or server. This helper copies the\n * key bytes but does not contact Solana or submit a transaction; the application\n * remains responsible for keeping the key secret.\n *\n * @param secretKeyBytes Secret Solana CLI-format 64-byte keypair held by the application.\n * @returns Deferred local signing configuration accepted by `createSolanaClient`.\n * @throws BridgeError When the key is not exactly 64 bytes.\n * @example const account = solanaKeyPair(secretKeyBytes)\n */\nexport function solanaKeyPair(secretKeyBytes: Uint8Array): SolanaAccount {\n if (secretKeyBytes.length !== 64) throw new BridgeError('Solana secret key must contain exactly 64 bytes')\n return { type: 'local', secretKeyBytes: new Uint8Array(secretKeyBytes) }\n}\n\n/**\n * Creates the Solana client used to read bridge state and optionally authorize transactions.\n *\n * Construction wires the transport and optional account without making an RPC\n * request. Read-only actions need only the transport; fund-moving actions also\n * require a Wallet Standard account or local keypair.\n *\n * @param config Solana network access and optional wallet authorization supplied by the application.\n * @returns Solana read, broadcast, and optional wallet capabilities used by bridge actions.\n * @throws BridgeError When the transport is absent.\n * @example const client = createSolanaClient({ transport: solanaHttp(rpcUrl), account: solanaKeyPair(key) })\n */\nexport function createSolanaClient(\n config: SolanaClientConfig,\n): SolanaClient {\n if (!config.transport) throw new BridgeError('Solana client requires a transport')\n return materializeSolanaClient(config, globalThis.fetch)\n}\n\n/** Normalizes HTTP, custom RPC, Wallet Standard, and local-key inputs behind the bridge's Solana capabilities. */\nfunction materializeSolanaClient(\n config: SolanaClientConfig,\n defaultFetch: SolanaRpcHttpTransport,\n): SolanaClient {\n const transportDefinition = config.transport\n // Adapt custom method/parameter transports to the fetch-like boundary shared\n // by the RPC reader, keeping response validation in one implementation.\n const httpTransport: SolanaRpcHttpTransport = transportDefinition.type === 'http'\n ? transportDefinition.fetch ?? defaultFetch\n : async (_url, init) => {\n const body = JSON.parse(init.body) as { method: string; params: unknown[] }\n return { ok: true, status: 200, json: async () => ({ result: await transportDefinition.request(body.method, body.params) }) }\n }\n const url = transportDefinition.type === 'http' ? transportDefinition.url : 'solana:custom'\n const rpcClient = createSolanaRpcClient({ url, transport: httpTransport })\n const publicClient: SolanaPublicClient = {\n ...rpcClient,\n async sendTransaction(signedTransaction) {\n // Solana's RPC accepts the complete wire transaction as base64. This path\n // never signs; callers must supply all required signatures first.\n const base64 = btoa(String.fromCharCode(...signedTransaction))\n const sendOptions = { encoding: 'base64', preflightCommitment: 'confirmed' }\n if (transportDefinition.type === 'custom') {\n const signature = await transportDefinition.request('sendTransaction', [base64, sendOptions])\n if (typeof signature !== 'string' || !signature) throw new BridgeError('Solana RPC sendTransaction returned an invalid signature')\n return { signature }\n }\n const response = await httpTransport(url, {\n method: 'POST',\n headers: { 'content-type': 'application/json', 'cache-control': 'no-cache' },\n body: JSON.stringify({ jsonrpc: '2.0', id: 1, method: 'sendTransaction', params: [base64, sendOptions] }),\n cache: 'no-store',\n })\n const body = await response.json() as { result?: unknown; error?: { message?: string; data?: unknown } }\n if (!response.ok || body.error || typeof body.result !== 'string' || !body.result) {\n const details = body.error?.data === undefined ? '' : `; ${JSON.stringify(body.error.data)}`\n throw new BridgeError(`Solana RPC sendTransaction failed: ${body.error?.message ?? `HTTP ${response.status}`}${details}`)\n }\n return { signature: body.result }\n },\n }\n\n let walletClient: SolanaWalletClient | undefined\n if (config.account?.type === 'wallet') {\n const walletAccount = config.account\n const feature = walletAccount.wallet.features[SOLANA_SIGN_AND_SEND_TRANSACTION_FEATURE] as\n | SolanaSignAndSendTransactionFeature\n | undefined\n if (!feature) throw new BridgeError(`Connected wallet does not expose the '${SOLANA_SIGN_AND_SEND_TRANSACTION_FEATURE}' feature`)\n // Wallet Standard combines authorization and broadcast. Preserve that\n // boundary because browser wallets do not expose private signing keys.\n walletClient = {\n getAddress: async () => walletAccount.account.address,\n sendTransaction: async (transaction) => {\n const [output] = await feature.signAndSendTransaction({\n transaction,\n account: walletAccount.account,\n chain: walletAccount.chain,\n })\n if (!output) throw new BridgeError('Wallet returned no signAndSendTransaction result')\n return { signature: bs58.encode(output.signature) }\n },\n }\n } else if (config.account?.type === 'local') {\n // Import the secret key lazily so creating a read/write client performs no\n // cryptographic setup until an address or signature is requested.\n let signerPromise: ReturnType<typeof createSigner> | undefined\n const create = () => signerPromise ??= createSigner(config.account!.type === 'local'\n ? config.account!.secretKeyBytes\n : new Uint8Array())\n walletClient = {\n getAddress: async () => (await create()).address,\n sendTransaction: async (wireTransaction) => {\n // Protocol code may have already added ephemeral signer signatures.\n // Partial signing adds the fee payer without discarding those bytes.\n const kit = await loadKit()\n const signer = await create()\n const transaction = kit.getTransactionDecoder().decode(wireTransaction)\n const signed = await kit.partiallySignTransaction([signer.keyPair], transaction)\n return publicClient.sendTransaction(new Uint8Array(kit.getTransactionEncoder().encode(signed)))\n },\n }\n }\n return { family: 'solana', publicClient, walletClient }\n}\n\nasync function createSigner(secretKeyBytes: Uint8Array) {\n const kit = await loadKit()\n return kit.createKeyPairSignerFromBytes(secretKeyBytes)\n}\n"],"mappings":"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","names":["offset","hexToBytes","hexToBytes"]}
|