Docs
How to query Axiom from any dApp, agent, or script — and how to embed Venice AI inference + x402 micropayments into your own project.
Axiom is a permissionless AI inference gateway that lets any on-chain agent or dApp pay for AI queries using x402 — an HTTP-native micropayment protocol. There is no subscription, no API key, and no custodial account. Every query costs a fraction of a cent in USDC, settled on Base Sepolia.
Under the hood, Axiom routes inference through Venice AI — a privacy-first, uncensored AI platform — and settles payments via MetaMask Smart Accounts using ERC-7710 delegations so users only sign once per session.
Venice AI
LLM, image, and audio inference
x402 Protocol
HTTP-native pay-per-call payments
MetaMask Smart Account
ERC-7710 session delegation
Client sends a POST request
Your app or agent sends a prompt to /api/infer. No auth headers needed on the first call.
Server returns HTTP 402
Axiom responds with payment requirements — the USDC amount, contract address, and facilitator URL.
Wallet pays via x402
The MetaMask Smart Account (or any x402 client) signs and broadcasts a micropayment using an existing ERC-7710 delegation.
Venice AI runs inference
Once payment is verified, the prompt is forwarded to Venice AI. Text, image, and audio models are all supported.
Response + settlement returned
The AI response is returned to the client. 1Shot relays the on-chain settlement — gas paid in USDC, no ETH required.
Venice AI provides privacy-preserving inference. Prompts are never logged or used for training. Axiom exposes three Venice modalities:
Text Chat
POST /api/venice/chat
OpenAI-compatible chat completions endpoint.
venice-uncensored, llama-3.3-70b, qwen-2.5-coder-32b
Image Generation
POST /api/venice/image/generate
Generate images from text prompts. Returns base64-encoded PNG/WebP.
grok-imagine-image, venice-sd35
Audio TTS
POST /api/venice/audio/speech
Text-to-speech with multiple voices. Returns MP3 audio.
tts-kokoro, tts-xai-v1
x402 Balance
GET /api/venice/x402/balance/{address}
Check a wallet's Venice credit balance. Requires SIWX auth.
x402 Transactions
GET /api/venice/x402/transactions/{address}
Paginated credit ledger. Requires SIWX auth.
x402 is an extension of HTTP 402 Payment Required. A server advertises payment requirements in the response body. The client pays on-chain and retries with an X-PAYMENT header. No browser popups, no approval UI on every call — just a signed USDC transfer on Base Sepolia.
{
"x402Version": 2,
"accepts": [{
"scheme": "exact",
"network": "eip155:84532",
"maxAmountRequired": "10000", // 0.01 USDC (6 decimals)
"asset": "0x036CbD53842c5426634e7929541eC2318f3dCF7e",
"payTo": "0xYOUR_PAYOUT_ADDRESS",
"resource": "/api/infer",
"description": "Axiom AI inference — pay per query"
}]
}const res = await fetch("/api/infer", {
method: "POST",
headers: { "Content-Type": "application/json" },
body: JSON.stringify({ prompt, model }),
});
if (res.status === 402) {
const { accepts } = await res.json();
// sign payment with your wallet / x402 client
const payment = await x402Client.pay(accepts[0]);
const paidRes = await fetch("/api/infer", {
method: "POST",
headers: {
"Content-Type": "application/json",
"X-PAYMENT": JSON.stringify(payment),
},
body: JSON.stringify({ prompt, model }),
});
return paidRes.json();
}Copy the snippets below to add Axiom inference into any dApp.
// No SDK needed — just fetch()
export async function queryAxiom(
prompt: string,
model = "venice-uncensored",
axiomBaseUrl = "https://your-axiom.vercel.app"
) {
const endpoint = `${axiomBaseUrl}/api/infer`;
// 1. Probe — expect 402
const probe = await fetch(endpoint, {
method: "POST",
headers: { "Content-Type": "application/json" },
body: JSON.stringify({ prompt, model }),
});
if (probe.ok) return probe.json();
if (probe.status !== 402) {
throw new Error(`Unexpected status: ${probe.status}`);
}
const { accepts } = await probe.json();
// 2. Pay using your preferred x402 client or wallet
const payment = await yourX402Client.pay(accepts[0]);
// 3. Retry with payment header
const res = await fetch(endpoint, {
method: "POST",
headers: {
"Content-Type": "application/json",
"X-PAYMENT": JSON.stringify(payment),
},
body: JSON.stringify({ prompt, model }),
});
if (!res.ok) throw new Error(`Inference failed: ${res.status}`);
return res.json();
// { result: string, model: string, latency: string, txHash: string }
}import { useState, useCallback } from "react";
import { queryAxiom } from "./queryAxiom";
export function useAxiom(model?: string) {
const [loading, setLoading] = useState(false);
const [error, setError] = useState<string | null>(null);
const [result, setResult] = useState<string | null>(null);
const query = useCallback(async (prompt: string) => {
setLoading(true);
setError(null);
try {
const data = await queryAxiom(prompt, model);
setResult(data.result);
return data;
} catch (e) {
const msg = e instanceof Error ? e.message : "Unknown error";
setError(msg);
} finally {
setLoading(false);
}
}, [model]);
return { query, result, loading, error };
}
// Usage:
// const { query, result, loading } = useAxiom("llama-3.3-70b");
// await query("Explain ERC-7710 in one sentence");const BASE = "https://your-axiom.vercel.app";
// Text chat
export const chat = (messages: { role: string; content: string }[], model: string) =>
fetch(`${BASE}/api/venice/chat`, {
method: "POST",
headers: { "Content-Type": "application/json" },
body: JSON.stringify({ model, messages }),
}).then((r) => r.json());
// Image generation
export const generateImage = (prompt: string, model = "grok-imagine-image") =>
fetch(`${BASE}/api/venice/image/generate`, {
method: "POST",
headers: { "Content-Type": "application/json" },
body: JSON.stringify({ model, prompt, width: 512, height: 512 }),
}).then((r) => r.json());
// returns { images: string[] } (base64)
// Text-to-speech
export const speak = (text: string, voice = "af_sky") =>
fetch(`${BASE}/api/venice/audio/speech`, {
method: "POST",
headers: { "Content-Type": "application/json" },
body: JSON.stringify({ model: "tts-kokoro", input: text, voice }),
}).then((r) => r.blob());
// returns Blob — create URL with URL.createObjectURL(blob)# Step 1 — probe (expect 402)
curl -X POST https://your-axiom.vercel.app/api/infer \
-H "Content-Type: application/json" \
-d '{"prompt": "What is Base chain?", "model": "venice-uncensored"}'
# Step 2 — retry with payment (replace <PAYMENT_JSON> with signed x402 payload)
curl -X POST https://your-axiom.vercel.app/api/infer \
-H "Content-Type: application/json" \
-H "X-PAYMENT: <PAYMENT_JSON>" \
-d '{"prompt": "What is Base chain?", "model": "venice-uncensored"}'
# Venice image generation (no x402 required)
curl -X POST https://your-axiom.vercel.app/api/venice/image/generate \
-H "Content-Type: application/json" \
-d '{"model": "grok-imagine-image", "prompt": "A neon cityscape on Base chain"}'Main inference endpoint. Returns 402 on first call, response on paid retry.
OpenAI-compatible chat completions via Venice AI.
Generate images. Returns base64-encoded image array.
List available image style presets.
Text-to-speech. Returns binary MP3/audio.
Get Venice credit balance for a wallet address.
Top up Venice credit balance via X-402-Payment header.
Paginated transaction history for a wallet.