Quickstart
From sign-in to a first swap on Base. Allow a few minutes, plus the time until your app is approved.
Your own fee per trade: add swapFeeRecipient and swapFeeBps to price and quote (see Swap). Not in v1: exact-out (buyAmount) and the /swap/permit2/* endpoints.
1. Sign in and create an app
- Open dashboard.qiguard.com and choose Continue with MetaMask. Complete the human check, then sign the sign-in message in MetaMask. Signing sends no transaction and costs no gas.
- Enter your team name and project type (wallet, DEX, bot, platform or other). A contact email is optional.
- Create an app: give it a name, pick the products (
swap,gasless) and the chains. - The app starts as
pending. Keys of a pending app answer403 APP_NOT_APPROVED; they work as soon as the app is approved. Adding a product or a chain to an approved app later sends it back for review.
2. Create a key
Open the app, tab Keys, and choose Create key. The key (qg_sk_...) is shown once: copy it into your server's secret store. Qiguard keeps only a keyed hash of it.
Secret keys are for servers. A secret key sent by a browser (an Origin header together with Sec-Fetch-Mode: cors) is refused with 403 ORIGIN_NOT_ALLOWED.
3. First calls
Keyless calls need no header:
curl -s https://api.qiguard.com/swap/chains
curl -s "https://api.qiguard.com/tokens?chainId=8453"
A price for 25 USDC to WETH on Base:
curl -s "https://api.qiguard.com/swap/allowance-holder/price?chainId=8453&sellToken=0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913&buyToken=0x4200000000000000000000000000000000000006&sellAmount=25000000" \
-H "qg-api-key: $QG_API_KEY" -H "qg-version: v1"
buyAmount and minBuyAmount are net amounts, after the on-chain fee in fees.qiguardFee.
4. Install the SDK
The JavaScript SDK is one file with no dependencies (Node 18+, Workers, browsers for keyless calls). Download it, with its type declarations, next to your code:
curl -sO https://docs.qiguard.com/sdk/qiguard-sdk.mjs
curl -sO https://docs.qiguard.com/sdk/qiguard-sdk.d.ts
| File | SHA-256 |
|---|---|
| qiguard-sdk.mjs | a444094cbd4d19133b9e3e801a75b284f68aead5b825fb72cfdc8de744583459 |
| qiguard-sdk.d.ts | b5b6b75341b9e514e4e3b14673b6e4f4881e2a2ad95554a3fb2477aeebd1e963 |
Then import it by path: import { QiguardClient } from './qiguard-sdk.mjs';.
5. Quote, approve, send
- Call
GET /swap/allowance-holder/quotewith the same parameters plustaker(the wallet that sends the trade). - If
issues.allowanceis set, the taker approvesissues.allowance.spender(the settlement contract) for exactlysellAmount, and waits for the approval receipt. - Quote again: the transaction carries a deadline (
expiresAt, 120 seconds by default). - Check that
transaction.tois the settlement contract of the chain (Contracts and fees), then sendtransactionas returned:to,data,value, andgasas the gas limit.
With the SDK and viem (npm install viem; TAKER_KEY is the private key of the trading wallet, kept in your own secret store):
import { createWalletClient, createPublicClient, http } from 'viem';
import { privateKeyToAccount } from 'viem/accounts';
import { base } from 'viem/chains';
import { QiguardClient, approvalsForQuote, assertSwapQuote } from './qiguard-sdk.mjs';
const account = privateKeyToAccount(process.env.TAKER_KEY); // your wallet
const wallet = createWalletClient({ account, chain: base, transport: http() });
const reader = createPublicClient({ chain: base, transport: http() });
const sendAndWait = async (tx) => {
const hash = await wallet.sendTransaction({ to: tx.to, data: tx.data, value: BigInt(tx.value), gas: tx.gas ? BigInt(tx.gas) : undefined });
return reader.waitForTransactionReceipt({ hash });
};
const qg = new QiguardClient({ apiKey: process.env.QG_API_KEY });
const taker = account.address;
const params = {
chainId: 8453,
sellToken: '0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913', // USDC
buyToken: '0x4200000000000000000000000000000000000006', // WETH
sellAmount: '25000000',
taker,
};
let quote = await qg.getQuote(params);
// exact-amount approvals, only ever for the settlement contract pinned in the SDK
for (const tx of approvalsForQuote(quote, { chainId: params.chainId })) await sendAndWait(tx);
quote = await qg.getQuote(params);
assertSwapQuote(quote, { chainId: params.chainId, sellToken: params.sellToken, buyToken: params.buyToken, sellAmount: params.sellAmount });
const receipt = await sendAndWait(quote.transaction);
console.log(receipt.status, receipt.transactionHash);
Complete scripts: swap-viem.mjs (this flow) and gasless-viem.mjs (gasless, with the checks before signing). They import ./qiguard-sdk.mjs from the same folder.
6. Check the dashboard
The Usage tab of the app shows requests per hour, errors and latency per endpoint. The Audit log lists sign-ins, key changes and app decisions.
Next
- Swap for every parameter and response field.
- Gasless to let takers trade without holding gas.
- Errors for every error name.
This page as Markdown: quickstart.md. All pages for tools: llms.txt.