Config
createConfig is the entry point to @symmio/trading-core. It returns an immutable Config object that every standalone action and TanStack Query / Mutation options factory receives as its first argument.
The config does not own viem clients — the framework layer (or a plain Node script) injects them via resolver callbacks. This keeps the SDK framework-agnostic and lets @symmio/trading-react bridge to wagmi without pulling wagmi into core.
Import
import { createConfig, type Config } from "@symmio/trading-core";Usage
import { createConfig, SymmioSupportedChainId } from "@symmio/trading-core";
import { createPublicClient, createWalletClient, http, zeroAddress } from "viem";
import { hyperEvm } from "viem/chains";
const publicClient = createPublicClient({ chain: hyperEvm, transport: http() });
const walletClient = createWalletClient({ account, chain: hyperEvm, transport: http() });
const config = createConfig({
symmioConfig: {
[SymmioSupportedChainId.HYPER_EVM]: {
// `zeroAddress` works out of the box (no fee share);
// swap in your registered affiliate to earn fees.
addresses: { affiliatesAddress: zeroAddress },
},
},
getClient: () => publicClient,
getWalletClient: async () => walletClient,
});The config is meant to be created once at app start and shared across every call. Do not recreate it per action — chain-config fingerprints (used in query keys) rebuild on every call to createConfig.
Parameters
symmioConfig
- Type:
Partial<Record<number, SymmioChainConfigInput>> - Required. Every supported chain must set
addresses.affiliatesAddress—createConfigthrowsAFFILIATE_ADDRESS_REQUIREDif it is missing. The zero address is accepted (a presence-only check) as a testing placeholder: on-chain it is treated as a no-affiliate sentinel, so the trade still opens — you just receive no share of the trading fee (nothing is attributed to you). What reverts is a non-zero unregistered affiliate: that fails on-chain withPartyAFacet: Invalid affiliateat trade time. Set your registered affiliate to actually earn the fee share.
SymmioChainConfigInput makes the affiliate mandatory in the type: every field is optional to override except addresses.affiliatesAddress, so a chain entry without an affiliate is a compile error.
Per-chain SYMMIO configuration, keyed by chain id, deep-merged onto the SDK’s built-in defaults. Each entry may override that chain’s addresses, subgraphs, solver, priceService, notifications, and muon endpoints — point at a staging subgraph, override an address, and so on.
Its one mandatory field is addresses.affiliatesAddress for every supported chain: your frontend’s on-chain affiliate (your identity in SYMMIO on that chain), attached to every quote (sendQuoteWithAffiliateAndData) so the protocol knows who sourced the trade and routes your share of the trading fee to you. Affiliate addresses are per chain — a registration on one chain is not valid on another. Registration lets your affiliate collect a share of the trading fees. Register your affiliate and set the registered address here.
The zero address is accepted as a no-affiliate test placeholder: trades still open, but you earn no share of the trading fee (it is not rejected and does not revert).
getClient
- Type:
(parameters?: { chainId?: number }) => PublicClient - Required
Resolves the viem PublicClient used for read actions. Called fresh on every read. Framework layers inject a chain-aware resolver — @symmio/trading-react bridges this to wagmi/actions#getPublicClient; a plain Node script returns its own viem client.
getWalletClient
- Type:
(parameters: { chainId: number; from?: Address }) => Promise<SymmioWalletClient> - Optional — read-only configs may omit it; write / sign actions then throw
NO_WALLET_CLIENT.
Returns the bound viem WalletClient used to sign and send. The SDK does not pick between multiple wallets. The resolver receives the optional from (passed by the action) and is responsible for returning the right client — for example, a session-key wallet when from matches the session key, or the wagmi-connected wallet otherwise. The resolver is called fresh per action, so account switches propagate without recreating the config.
defaultChainId
- Type:
number - Default: first built-in supported chain
Chain used when an action or query omits chainId. Set to pin the SDK to a specific chain in single-chain apps.
simulateBeforeWrite
- Type:
boolean - Default:
true
Dry-run every write with viem’s simulateContract before sending it. Aborts (and throws the decoded revert) if the transaction would fail. Override for a single call with the write’s simulateBeforeWrite option; set false here to disable the pre-flight for all writes.
webSocketConstructor
- Type:
WebSocketConstructor - Default:
globalThis.WebSocket
WebSocket implementation used by streaming actions (watchNotifications, watchTpSlNotifications, watchPriceServiceStream). Set in browsers and Node 22+. Pass an implementation explicitly to run streams in older Node (the ws package) or a mock in tests.
Returns
The returned Config is immutable. It exposes:
Data
chains: readonly number[]— chain ids the config knows about.defaultChainId: number— the defaultchainIdused when actions omit it.simulateBeforeWrite: boolean— the default dry-run flag for writes.
Resolvers
getChainConfig(chainId?): SymmioChainConfig— fully-merged config for a chain. ThrowsUNSUPPORTED_CHAINwhen unknown.getChainConfigKey(chainId?): string— stable fingerprint of a chain’s resolved config, folded into every query key so overrides do not serve stale cache. Returns a"unsupported"sentinel for unknown chains (never throws).getClient({ chainId? }): PublicClient— resolves the read client.getWalletClient({ chainId?, from? }): Promise<SymmioWalletClient>— resolves the write client. ThrowsNO_WALLET_CLIENTwhengetWalletClientwas not supplied.getWebSocketConstructor(): WebSocketConstructor— returns the injected constructor or the globalWebSocket. ThrowsNO_WEBSOCKETwhen neither is available.
ConfigParameter
Every action and hook accepts a config?: Config override via the ConfigParameter mixin:
interface ConfigParameter {
/** Use this config instead of the one from context. */
config?: Config;
}In @symmio/trading-react the hook reads the config from context (via SymmioProvider) unless parameters.config is set — mirroring wagmi’s parameters.config ?? contextConfig pattern.
Errors
createConfig throws SymmError synchronously on:
AFFILIATE_ADDRESS_REQUIRED— a supported chain’ssymmioConfig[chainId].addresses.affiliatesAddresswas missing. (The zero address is accepted — see thesymmioConfignote.)NO_CHAINS_CONFIGURED— no supported chains in the built-in registry.
The Config throws on lazy resolution:
UNSUPPORTED_CHAIN— fromgetChainConfig(id)whenidis unknown.NO_WALLET_CLIENT— fromgetWalletClientwhen the resolver was not supplied.NO_WEBSOCKET— fromgetWebSocketConstructorwhen no constructor is available.
Related
- React provider —
SymmioProviderwrapscreateConfigfor React apps. - Query options — how the factories consume the config.
- Errors — full
SymmErrorcatalogue.