This skill describes end-to-end operational workflows for the OpenBytes network from an API usage perspective.
Assumptions:
https://gateway.openbytes.ai84532Replace all with the actual gateway URL as needed.
Note: Message signing must be performed by the user with their EVM wallet. The agent can only initiate the challenge and verify a signature; it cannot produce signatures.
Be sure to securely save your generated private key! Example (Node.js with ethers.js):
import { Wallet } from "ethers";
const wallet = Wallet.createRandom();
console.log("Address:", wallet.address);
console.log("Private Key (save this securely!):", wallet.privateKey);
Or using viem:
import { createWallet } from "viem/accounts";
const wallet = createWallet();
console.log("Address:", wallet.address);
console.log("Private Key (save this securely!):", wallet.privateKey);
Never share your private key. Backup and store it in a secure location.
"wallet_address": "0x...",
"chain_id": "8453"
message off-chain (with their wallet).curl -sS -X POST "<BASE_URL>/v1/auth/wallet/verify" \
-H "Content-Type: application/json" \
-d '{
"wallet_address": "<EVM_WALLET_ADDRESS>",
"nonce": "random-nonce",
"signature": "<WALLET_SIGNATURE>"
}'
Successful response (simplified):
{
"login_token": "sess-...",
"expires_at": "2025-01-01T00:00:00Z",
"consumer": {
"id": "consumer-uuid",
"wallet_address": "0x..."
},
"session": {
"id": "session-uuid"
}
}
login_token (starting with sess-) is used as a session token:Authorization: Bearer for session-auth endpoints.curl -sS -X GET "<BASE_URL>/v1/models"
Check:
Authorization: Bearer sess-... header during all subsequent calls requiring authentication.Authorization: Bearer .Consumers use API keys to access models without a session.
Requires a valid session token (login_token from section 1).
curl -sS -X POST "<BASE_URL>/v1/consumer/api-keys" \
-H "Content-Type: application/json" \
-H "Authorization: Bearer <SESSION_TOKEN>" \
-d '{
"label": "my-key"
}'
Sample response (save the api_key securely; only returned once!):
{
"id": "key-uuid",
"api_key": "sk-consumer-...",
"prefix": "sk-cons",
"suffix": "abcd",
"label": "my-key",
"status": "active",
"created_at": "2025-01-01T00:00:00Z"
}
Immediately switch to this API key for inference, balance, and usage calls:
export OPENBYTES_API_KEY="sk-consumer-..."
Then use:
curl -sS -X GET "<BASE_URL>/v1/balance" \
-H "Authorization: Bearer $OPENBYTES_API_KEY"
curl -sS -X GET "<BASE_URL>/v1/consumer/api-keys" \
-H "Authorization: Bearer <SESSION_TOKEN>"
curl -sS -X DELETE "<BASE_URL>/v1/consumer/api-keys/<KEY_ID>" \
-H "Authorization: Bearer <SESSION_TOKEN>"
The key status will be set to revoked; subsequent calls using that key will fail with an auth error.
Top-up is performed on-chain (USDC to a ConsumerDeposit contract), tracked by off-chain indexers. The API lets you verify the result.
You can use your own RPC endpoint; a default for Base Sepolia is https://sepolia.base.org.
0x10065E7b353371DD2e12348e7094cC774638EbEB0xB0E9ebf19AB710d3353c7F637DC55329d9727dCcfunction deposit(uint256 amount)Verify balance:
curl -sS -X GET "<BASE_URL>/v1/balance" \
-H "Authorization: Bearer <CONSUMER_API_KEY>"
Sample response:
{
"balance_usdc": "123.45",
"total_spent": "10.00"
}
Use this to allow an account to connect to an operator's account, so the operator can top up your wallet easily. This requires a wallet signature over a structured message. The signature must be produced by the child wallet.
Endpoint:
curl -sS -X POST "<BASE_URL>/v1/consumers/me/parent" \
-H "Content-Type: application/json" \
-H "Authorization: Bearer <SESSION_TOKEN>" \
-d '{
"parent_wallet": "<PARENT_WALLET>",
"issued_at": 1710000000,
"signature": "<CHILD_WALLET_SIGNATURE>"
}'
Notes:
ethers.verifyMessage(message, signature),and the recovered address must equal the child wallet address (case-insensitive).
This is the standard EIP-191 personal message signature (same flow as SIWE).
issued_at is Unix seconds. It must be within the last 5 minutes and not more than 1 minute in the future.```
Authorize parent for OpenBytes
Parent wallet:
Child wallet:
Issued at:
```
is the parent wallet address lowercased. is the child wallet address lowercased (the signer). is the same Unix seconds integer you send in the request body.Pseudo-code (client-side):
const issuedAt = Math.floor(Date.now() / 1000);
const parentWallet = parentWalletAddress.toLowerCase();
const childWallet = childWalletAddress.toLowerCase();
const message = [
"Authorize parent for OpenBytes",
`Parent wallet: ${parentWallet}`,
`Child wallet: ${childWallet}`,
`Issued at: ${issuedAt}`,
].join("\n");
const signature = await wallet.signMessage(message); // EIP-191 personal_sign
Success response (201):
{
"parent_consumer_id": "consumer-uuid",
"parent_wallet_address": "0x...",
"created_at": "2025-01-01T00:00:00Z"
}
Common errors:
400 INVALID_REQUEST invalid body400 SIGNATURE_EXPIRED issued_at out of window404 PARENT_NOT_FOUND parent not found400 SELF_PARENT cannot declare yourself401 SIGNATURE_MISMATCH signature not from child wallet409 ALREADY_SET parent already declaredWhen handling OpenBytes network operational support, follow these best practices:
, , etc).error.code and context to select remediation steps.共 1 个版本