Code Examples
Code examples
The fastest way to see every SDK call in action is the reference console app. It consumes @symmio/trading-core and @symmio/trading-react exactly the way a third-party integrator would, and drives real contract reads and writes, deposits, quotes, and positions:
Live console: https://console.trading-sdk.symm.io
Source (monorepo): https://github.com/SYMM-IO/Trading-SDK
UI component explorer (Storybook): https://symmio-frontier-storybook.vercel.app
Minimal headless bot (end-to-end)
A single-file bot that sets up once, opens one position, and sketches how to manage and close it. It uses @symmio/trading-core and @symmio/session-key, and assumes the SubAccount was already created (see Part 1).
import {
createConfig, SymmioSupportedChainId,
getUserSubAccounts, grantDelegation, getIsDelegationActive,
INSTANT_TRADE_REQUIRED_SELECTORS,
getMarkets, watchEnigmaPrices,
instantOpenAuto, instantCloseAuto, setQuoteTpSl, PositionType,
} from "@symmio/trading-core";
import { createSessionKeyManager } from "@symmio/session-key";
import { createPublicClient, http } from "viem";
const OWNER = "0xYourOwnerEOA";
const publicClient = createPublicClient({ transport: http("https://rpc.hyperliquid.xyz/evm") });
const config = createConfig({
symmioConfig: {
[SymmioSupportedChainId.HYPER_EVM]: { addresses: { affiliatesAddress: "0xYourAffiliate" } },
},
defaultChainId: SymmioSupportedChainId.HYPER_EVM,
getClient: () => publicClient,
getWalletClient: async ({ chainId, from }) => resolveWalletClient({ chainId, from }),
});
async function main() {
const [subAccount] = await getUserSubAccounts(config, { user: OWNER });
const manager = createSessionKeyManager({ storage });
const { address: sessionKey } = await manager.initialize(OWNER);
await grantDelegation(config, {
account: { addr: subAccount, isPartyB: false },
delegatedSigner: sessionKey,
selectors: INSTANT_TRADE_REQUIRED_SELECTORS, // three selectors: open, add margin, close
expiryTimestamp: 1_766_000_000n,
});
// getIsDelegationActive checks one selector at a time; all must be true
const checks = await Promise.all(
INSTANT_TRADE_REQUIRED_SELECTORS.map((selector) =>
getIsDelegationActive(config, {
account: { addr: subAccount, isPartyB: false },
delegate: sessionKey,
selector,
})
)
);
if (!checks.every(Boolean)) throw new Error("delegation not active");
const symbols = await getMarkets(config, {});
const symbol = symbols[0];
const market = { id: symbol.symbol_id, name: symbol.name };
watchEnigmaPrices(config, { onPrices: (ticks) => {/* feed your strategy */} });
const { tempQuoteId } = await instantOpenAuto(config, {
from: sessionKey, subAccountAddress: subAccount,
market, positionType: PositionType.LONG,
initialMargin: "100", leverage: 5, slippage: 1,
});
console.log("opened, temp id:", tempQuoteId);
// Resolve the on-chain quoteId from watchNotifications/reconcileQuotes,
// and the position's Virtual Account from resolveQuoteAccounts, then:
// await setQuoteTpSl(config, {
// from: sessionKey, quoteId, virtualAccount, subAccount,
// symbolId: market.id, positionType: PositionType.LONG,
// quantity: "0.01", pricePrecision: symbol.price_precision,
// tp: { triggerPrice: "150", priceType: "markPrice" },
// });
// await instantCloseAuto(config, {
// from: sessionKey, partyA: virtualAccount, market, // partyA is the VA
// positionType: PositionType.LONG, quoteId, quantityToClose: "1", slippage: 1,
// });
}
main().catch(console.error);This is illustrative scaffolding, not a strategy. Add error handling (core throws
SymmError/SymmApiError; the React layer normalizes everything toSymmioRequestError), reconnection for the price and notification sockets, and your own risk logic before running with real funds.
Last updated

