Machine-native surface

Skill

Install the VeTrade Codex skill and connect it to the public MCP server.

The VeTrade Codex skill uses the public VeTrade MCP tools for instant-on planning, quote, read, prepare, and validation work, and can execute transfers, swaps, swap-transfers, or limit-order create or cancel flows locally with PRIVATE_KEY. Optional VIP-191 fee delegation stays local through GAS_PAYER_PRIVATE_KEY or gasPayerPrivateKeyFile.

Skill metadata

  • skill name: vetrade-ai
  • display name: VeTrade AI
  • trigger: VeTrade swap quotes, local swap execution, limit-order creation or cancellation, limit-order status reads, or bundle validation

When to use it

  • You need a quote-only plan
  • You need a wallet-bound clause bundle
  • You want to execute a swap locally with PRIVATE_KEY
  • You want to create a limit order locally with PRIVATE_KEY
  • You want to cancel a limit order locally with PRIVATE_KEY
  • You want a limit-order status or listing read
  • You want a validation pass before execution

Simple starting points

  • swap or trade request: start with hosted swap
  • direct send request: start with hosted transfer
  • recipient-bound swap with fixed input: start with hosted swap_transfer_exact_in
  • recipient-bound swap with fixed output: start with hosted swap_transfer_exact_out
  • quote-only request: start with local quote-swap or OpenAI local quote_swap
  • new limit order: start with hosted create_limit_order
  • cancel order: start with hosted cancel_limit_order
  • order reads: start with list_limit_orders or get_limit_order_status
  • managed execution: prefer quote-swap, transfer, swap-transfer-exact-in, swap-transfer-exact-out, create-limit-order, cancel-limit-order, cancel-all-limit-orders, and list-limit-orders
  • token lookup only: use resolve_supported_tokens
  • lower-level control: drop to quote_swap, prepare_swap_bundle, prepare_limit_order, or the inspect_*_readiness tools only when the default task tools are not enough

Default behavior

  • Keep quote, list, and detail requests read-only
  • Start with transfer, swap_transfer_exact_in, swap_transfer_exact_out, swap, create_limit_order, or cancel_limit_order when the user wants a direct planning or preflight result from human-friendly inputs
  • Use resolve_supported_tokens only when token lookup itself is the task or when an advanced flow genuinely needs explicit token metadata first
  • Use list_supported_token_refs when you want the compact registry list first
  • Use get_token_details only when you need richer metadata for one resolved token
  • Use get_wallet_balances when you want a read-only VET, VTHO, or supported-token balance preflight before execution
  • Use get_token_allowances when you want a read-only ERC20 approval check for a known owner and spender before execution
  • Use get_execution_readiness when you already have a prepared bundle and want one read-only answer about gas cost, balance sufficiency, allowance shortfalls, quote freshness, and readiness before local submission
  • Use the inspect_*_readiness MCP tools when the caller needs a summary-first answer and does not need the full prepared bundle payload
  • Keep list_supported_tokens available as the richer compatibility list when a client explicitly wants the full registry payload
  • Use the public VeTrade MCP server for instant-on task flows, advanced quote and prepare flows, validation, and read calls
  • Keep the public MCP server and HTTP APIs prepare/read-only
  • Execute locally only when the user clearly asks to transfer, swap, swap-transfer, create a limit order, or cancel a limit order

Local execution requirements

  • signer source: PRIVATE_KEY from the environment
  • fallback signer source: the mounted /mnt/session/uploads/vetrade/private_key.txt file through privateKeyFile
  • optional gas payer source: GAS_PAYER_PRIVATE_KEY from the environment
  • optional fallback gas payer source: GAS_PAYER_PRIVATE_KEY_FILE or gasPayerPrivateKeyFile
  • optional default gas mode: defaultGasPaymentMode with sender or gas_payer
  • optional per-call override: gasPaymentMode with inherit, sender, or gas_payer
  • default network: mainnet
  • default recipient or maker: the signer derived from PRIVATE_KEY
  • allow another final recipient only for transfer, swap-transfer-exact-in, and swap-transfer-exact-out; stop before submission for mismatched signer-bound recipient or maker values
  • estimate gas with thorClient.gas.estimateGas(clauses, sender, { gasPadding: 0.25 }) before signing

Use the returned bundle.rawClauses as the execution source of truth. Do not rebuild VeTrade clauses locally unless validation already failed.

Packaged local execution helper

The skill now ships a local helper script at https://vetrade.vet/skills/vetrade-ai/scripts/localExecution.mjs plus a pinned runtime bundle at https://vetrade.vet/skills/vetrade-ai/runtime.tar.gz.

Prefer the helper for local execution work instead of rewriting the VeChain SDK flow in each prompt:

node ~/.codex/skills/vetrade-ai/scripts/localExecution.mjs signer signer-input.json
node ~/.codex/skills/vetrade-ai/scripts/localExecution.mjs quote-swap quote-input.json
node ~/.codex/skills/vetrade-ai/scripts/localExecution.mjs swap swap-input.json
node ~/.codex/skills/vetrade-ai/scripts/localExecution.mjs transfer transfer-input.json
node ~/.codex/skills/vetrade-ai/scripts/localExecution.mjs swap-transfer-exact-in swap-transfer-in-input.json
node ~/.codex/skills/vetrade-ai/scripts/localExecution.mjs swap-transfer-exact-out swap-transfer-out-input.json
node ~/.codex/skills/vetrade-ai/scripts/localExecution.mjs preview execution-input.json
node ~/.codex/skills/vetrade-ai/scripts/localExecution.mjs submit-atomic execution-input.json
node ~/.codex/skills/vetrade-ai/scripts/localExecution.mjs submit execution-input.json
node ~/.codex/skills/vetrade-ai/scripts/localExecution.mjs execute execution-input.json
node ~/.codex/skills/vetrade-ai/scripts/localExecution.mjs receipt receipt-input.json

The helper accepts the prepared VeTrade bundle shape directly and adds:

  • signer and expected-recipient or maker checks
  • a dedicated signer command for deriving the signer address from PRIVATE_KEY or privateKeyFile
  • a high-level quote-swap command for human-friendly quote-only reads
  • a high-level swap command that uses the hosted swap MCP tool, derives the signer address locally, and submits in one serial process
  • a high-level transfer command that uses the hosted transfer MCP tool and preserves resolved recipient metadata
  • high-level swap-transfer-exact-in and swap-transfer-exact-out commands that use the hosted swap-transfer MCP tools and preserve resolved recipient metadata
  • a compact output mode for swap, preview, submit-atomic, submit, execute, and receipt so agents can keep execution results small
  • direct signer-file support through privateKeyFile
  • direct gas-payer-file support through gasPayerPrivateKeyFile
  • quote-freshness reporting
  • gas and VTHO preflight checks
  • fee-payer reporting so preview and execution results show whether gas came from the signer or delegated sponsor
  • economics checks for VTHO-denominated swaps so tiny trades can be reported clearly even when execution still proceeds
  • ERC-20 balance checks derived from bundle.decodedCalls or, when managed runtimes trim them, from the quote block
  • deterministic execution keys to avoid accidental duplicate sends
  • receipt parsing for swap settlement and OrderCreated
  • signer-facing settlement reporting for native VET outputs, while preserving reportedRecipient when the swap event points at an intermediate settlement address

Use quote-swap as the primary quote-only path when the user asks for a current value such as quote 1 VTHO to VET. Use swap as the primary live-swap path when the user names the swap in token-symbol terms and you want the helper to call the hosted swap tool, derive the signer address locally, and submit in one serial process. Use create-limit-order, cancel-limit-order, cancel-all-limit-orders, and list-limit-orders as the default one-shot limit-order management path. Use submit-atomic only when you already have a prepared and validated payload and want one serial shell block that reads it from stdin or a file. Use submit only when you already have the execution payload on disk and do not need the higher-level symbol-driven flow. All three reuse the same preflight checks as preview, then submit once the bundle is ready. Use preview only when you explicitly want a preflight-only answer or blocker diagnosis, and use execute only when you intentionally need the lower-level flow after an earlier preview decision. Set outputMode: "compact" in managed runtimes when the agent only needs signer, route summary, tx, settlement, fees, timings, warnings, and economics instead of the full receipt body. The hosted swap response now also exposes quote.validityWindowSeconds, quote.economicsHint, routeSummary.routeLabel, and routeSummary.symbolExecutionPath so route narration and quote-window reminders do not need ad-hoc string building in the prompt.

For quote-only reads, prefer the high-level quote-swap command first when the request is a straightforward symbol-driven quote such as 1 VTHO to VET. For live swaps, prefer the high-level swap command first when the request is a straightforward symbol-driven swap such as 1 VTHO to VET. If you need lower-level control, use hosted quote_swap or prepare_swap_bundle with include.simulation = true instead of rebuilding token resolution or route narration by hand. Keep the quote block in the helper payload when it is available, because managed runtimes may trim bundle.decodedCalls and the helper can fall back to quote metadata for swap intent and balance checks. In managed shells, keep the flow serial, pass the mounted signer file through privateKeyFile without reading or printing it, derive the signer through node ... signer instead of ad-hoc Python, Node, or shell crypto snippets, and prefer cat <<'JSON' | node ... quote-swap or cat <<'JSON' | node ... swap for the default symbol-driven paths. The helper derives the signer locally and binds that address into the hosted swap call, so callers do not need to pass recipient manually in the default local path. If the environment exposes HTTP_PROXY, HTTPS_PROXY, or ALL_PROXY, the CLI relaunches itself with --use-env-proxy automatically and suppresses the related experimental warning so the tool result stays compact.

Always report fees next to the received amount. Very small swaps can succeed on-chain and still be economically poor because gas dominates the trade size. When the helper says estimated gas cost exceeds the VTHO side of the trade, treat that as an explicit warning to report rather than a separate execution override.

The helper prefers the packaged runtime next to itself, so cold starts do not need npm install. Set VETRADE_EXECUTION_MODULE_ROOT only when you intentionally want to override that packaged runtime with another workspace such as the VeTrade website directory.

If you are not running in Codex, use the OpenAI SDK page for the self-hosted Node integration under agents/openai-sdk/.

The helper output now includes runtimeSource, timings.bootstrapMs, and timings.totalMs. Submission paths also include timings.submittedAt. Managed-agent sessions that download the published runtime to /tmp/vetrade/runtime report runtimeSource: downloaded, which lets operators distinguish that path from a packaged local skill install or a true custom override.

Canonical Node execution snippet

Use this only as the fallback path when the packaged helper script is unavailable and another agent still needs a copyable local execution path with the VeChain SDK.

import { Address, Hex } from '@vechain/sdk-core';
import { ThorClient, VeChainPrivateKeySigner, VeChainProvider } from '@vechain/sdk-network';

type PreparedClause = {
  to: string;
  value?: string;
  data?: string;
};

type ExecutePreparedClausesInput = {
  rawClauses: PreparedClause[];
  expectedSigner?: string;
  networkUrl?: string;
};

export async function executePreparedClauses({
  rawClauses,
  expectedSigner,
  networkUrl = 'https://mainnet.vechain.org',
}: ExecutePreparedClausesInput) {
  const privateKey = process.env.PRIVATE_KEY;
  if (privateKey === undefined || privateKey.trim() === '') {
    throw new Error('You need to export PRIVATE_KEY before executing VeTrade clauses locally.');
  }

  const thorClient = ThorClient.at(networkUrl);
  const provider = new VeChainProvider(thorClient);
  const signer = new VeChainPrivateKeySigner(Hex.of(privateKey).bytes, provider);
  const signerAddress = await signer.getAddress();

  if (expectedSigner !== undefined) {
    const actual = Address.checksum(Hex.of(signerAddress));
    const expected = Address.checksum(Hex.of(expectedSigner));
    if (actual !== expected) {
      throw new Error(
        `You need to use PRIVATE_KEY for ${expected} or prepare a new VeTrade bundle for ${actual}.`
      );
    }
  }

  const clauses = rawClauses.map((clause) => ({
    to: clause.to,
    value: clause.value ?? '0x0',
    data: clause.data ?? '0x',
  }));

  const gasEstimate = await thorClient.gas.estimateGas(clauses, signerAddress, {
    gasPadding: 0.25,
  });

  const nextBaseFeePerGas = (await thorClient.gas.getNextBlockBaseFeePerGas()) ?? 0n;
  const estimatedGasCost = BigInt(gasEstimate.totalGas) * nextBaseFeePerGas;
  const account = await thorClient.accounts.getAccount(Address.of(signerAddress));
  const availableVtho = BigInt(account.energy);

  if (availableVtho < estimatedGasCost) {
    throw new Error(
      `You need at least ${estimatedGasCost.toString()} wei of VTHO for gas, but only ${availableVtho.toString()} is available.`
    );
  }

  const txId = await signer.sendTransaction({
    from: signerAddress,
    clauses,
  });

  const receipt = await thorClient.transactions.waitForTransaction(txId, {
    intervalMs: 2_000,
    timeoutMs: 120_000,
  });

  if (receipt === null) {
    throw new Error(
      `Transaction ${txId} was submitted, but the receipt did not arrive in time. You need to query the transaction on-chain and rerun the receipt check.`
    );
  }

  if (receipt.reverted) {
    throw new Error(
      `Transaction ${txId} reverted on-chain. You need to inspect the receipt outputs and the prepared VeTrade bundle before retrying.`
    );
  }

  return {
    txId,
    signer: signerAddress,
    gasEstimate: gasEstimate.totalGas.toString(),
    estimatedGasCost: estimatedGasCost.toString(),
    receipt,
  };
}

// Example:
// await executePreparedClauses({
//   rawClauses: bundle.rawClauses,
//   expectedSigner: bundle.recipient ?? bundle.maker,
// });

Codex bootstrap prompt

Paste this into another Codex instance if you want Codex to install the skill and MCP entry for you:

Install the VeTrade AI Codex skill from the public VeTrade docs and configure its MCP server.
VeTrade is the VeChain DEX aggregator surface for swap, trade, quote, and limit-order functions.
1. Create `~/.codex/skills/vetrade-ai/agents`, `~/.codex/skills/vetrade-ai/scripts`, and `~/.codex/skills/vetrade-ai/runtime`.
2. Download:
   - `https://vetrade.vet/skills/vetrade-ai/SKILL.md`
   - `https://vetrade.vet/skills/vetrade-ai/agents/openai.yaml`
   - `https://vetrade.vet/skills/vetrade-ai/scripts/localExecution.mjs`
   - `https://vetrade.vet/skills/vetrade-ai/runtime.tar.gz`
3. Save them to:
   - `~/.codex/skills/vetrade-ai/SKILL.md`
   - `~/.codex/skills/vetrade-ai/agents/openai.yaml`
   - `~/.codex/skills/vetrade-ai/scripts/localExecution.mjs`
   - extract `runtime.tar.gz` into `~/.codex/skills/vetrade-ai/runtime`
4. Update `~/.codex/config.toml` so it contains:
[mcp_servers.vetrade_ai]
url = "https://mcp.vetrade.vet"
5. If you want local execution, export `PRIVATE_KEY` before starting a fresh Codex process.
6. Do not run `npm install` for the helper runtime. Use `VETRADE_EXECUTION_MODULE_ROOT` only if you intentionally want to override the packaged runtime with the VeTrade `website` directory or another custom workspace.
7. If the MCP stanza already exists, keep a single correct entry instead of duplicating it.
8. After the files are in place, report exactly what changed and remind me to restart Codex.

Terminal install commands

Paste this into a terminal if you want a direct local install:

# Install VeTrade, the VeChain DEX aggregator skill for swaps, trading, quotes, and limit orders in Codex.
mkdir -p ~/.codex/skills/vetrade-ai/agents ~/.codex/skills/vetrade-ai/scripts ~/.codex/skills/vetrade-ai/runtime
curl -fsSL https://vetrade.vet/skills/vetrade-ai/SKILL.md \
  -o ~/.codex/skills/vetrade-ai/SKILL.md
curl -fsSL https://vetrade.vet/skills/vetrade-ai/agents/openai.yaml \
  -o ~/.codex/skills/vetrade-ai/agents/openai.yaml
curl -fsSL https://vetrade.vet/skills/vetrade-ai/scripts/localExecution.mjs \
  -o ~/.codex/skills/vetrade-ai/scripts/localExecution.mjs
curl -fsSL https://vetrade.vet/skills/vetrade-ai/runtime.tar.gz \
  -o /tmp/vetrade-runtime.tar.gz
tar -xzf /tmp/vetrade-runtime.tar.gz -C ~/.codex/skills/vetrade-ai
rm -f /tmp/vetrade-runtime.tar.gz
touch ~/.codex/config.toml
grep -q '^\[mcp_servers\.vetrade_ai\]$' ~/.codex/config.toml || cat >> ~/.codex/config.toml <<'EOF'
[mcp_servers.vetrade_ai]
url = "https://mcp.vetrade.vet"
EOF
After install, restart Codex and use the VeTrade AI skill with these MCP-backed tools:
- quote_swap
- prepare_swap_bundle
- validate_swap_bundle
- prepare_limit_order
- list_limit_orders
- prepare_limit_order_cancellation
- get_limit_order_status
- list_supported_token_refs
- get_token_details
- resolve_supported_tokens
- get_wallet_balances
- get_token_allowances
- get_execution_readiness
- list_supported_tokens

For local execution prompts, export PRIVATE_KEY before starting the fresh Codex process, or pass privateKeyFile when the signer is mounted into a managed session. If you want delegated gas, also export GAS_PAYER_PRIVATE_KEY or pass gasPayerPrivateKeyFile, then choose defaultGasPaymentMode: "gas_payer" or a per-call gasPaymentMode. The packaged runtime is the default cold-start path, so only set VETRADE_EXECUTION_MODULE_ROOT=/absolute/path/to/website when you intentionally want to override it.

Use a fresh codex exec process so the MCP config is loaded from ~/.codex/config.toml. Do not reuse a long-running session for newly added MCP config or skill files.

Each example below shows the natural-language prompt first, then the intended Codex result format. Keep the checklist, tool calls, and final answer block when you replace the result templates with live runs.

Quotes

Prompt

Using vetrade skills, how much worth is 1 B3TR in VET currently vechain?

Result

• I’m using the vetrade-ai skill and will pull a live VeTrade quote for 1 B3TR -> VET, then convert that into a plain current-value answer with exact token context.

• Updated Plan
  └ □ Read the VeTrade skill instructions and confirm the token registry workflow
    □ Fetch the supported-token registry and identify B3TR/VET token metadata
    □ Request a live quote for 1 B3TR to VET and answer with the current value

• Called vetrade_ai.list_supported_tokens({})
  └ {"tokens":[...]}

• Updated Plan
  └ ✔ Read the VeTrade skill instructions and confirm the token registry workflow
    ✔ Fetch the supported-token registry and identify B3TR/VET token metadata
    □ Request a live quote for 1 B3TR to VET and answer with the current value

• Called vetrade_ai.quote_swap({"amountIn":"1000000000000000000","inputToken":"0x5ef79995fe8a89e0812330e4378eb2660cede699","outputToken":"0x0000000000000000000000000000000000000000","slippageBps":100})
  └ {"apiVersion":"v2","mode":"quote_only",...}

• Updated Plan
  └ ✔ Read the VeTrade skill instructions and confirm the token registry workflow
    ✔ Fetch the supported-token registry and identify B3TR/VET token metadata
    ✔ Request a live quote for 1 B3TR to VET and answer with the current value

• 1 B3TR is currently worth about 1.3546 VET on VeTrade.

  - Exact quote: 1.354583488113469118 VET
  - Minimum out at 1% slippage: 1.341037653232334426 VET
  - Quote generated: 2026-03-25 14:01:09 UTC
  - Valid until: 2026-03-25 14:02:09 UTC
  - Route: direct B3TR -> VET swap via VeRocketFactory

  Warning: this was a quote-only check, so no executable wallet bundle was requested.

Swaps

Prompt

Using vetrade skills. Swap 1 VTHO to VET at the current rate. My private key is in env PRIVATE_KEY.

Result

• I’m using the vetrade-ai skill for an execution-capable VeTrade flow. I’ll resolve token metadata, derive the signer from PRIVATE_KEY, prepare and validate a fresh bundle, run local preflight checks, and submit the swap on VeChain mainnet.

• Updated Plan
  └ □ Resolve VTHO and VET metadata
    □ Derive the signer address from PRIVATE_KEY
    □ Prepare a wallet-bound VeTrade bundle with simulation
    □ Validate the rawClauses and run one local helper submission
    □ Submit the transaction and summarize settlement

• Called vetrade_ai.list_supported_tokens({})
  └ {"tokens":[...]}

• Ran a local signer derivation with PRIVATE_KEY
  └ {"signer":"0xYourSignerAddress"}

• Called vetrade_ai.prepare_swap_bundle({...,"recipient":"0xYourSignerAddress","include":{"simulation":true}})
  └ {"apiVersion":"v2","mode":"wallet_bound","bundle":{"rawClauses":[...]},"simulation":{"success":true,...}}

• Called vetrade_ai.validate_swap_bundle({...})
  └ {"success":true,...}

• Ran node ~/.codex/skills/vetrade-ai/scripts/localExecution.mjs submit
  └ {"txId":"0x...","preview":{"readyToSubmit":true,...},"receipt":{"reverted":false,...}}

• Swap executed on VeChain mainnet.

  - Transaction: 0x...
  - Quote generated: 2026-04-01 00:00:00 UTC
  - Valid until: 2026-04-01 00:01:00 UTC
  - Input: 1 VTHO
  - Quoted output: ...
  - Minimum output at 1% slippage: ...
  - Route: ...
  - Bundle clauses: ...
  - Simulation: success, no warnings
  - Settlement: ...
  - Gas used: ...
  - Actual fee paid: ...

Limit order creation

Prompt

Using vetrade skills. Create a VeChain limit order that sells 500 VTHO for 500 VET. My private key is in env PRIVATE_KEY.

Result

• I’m using the vetrade-ai skill for a local VeTrade limit-order execution. I’ll derive the signer from PRIVATE_KEY, use it as the maker, prepare and validate the order bundle, submit it locally, then confirm the created order on-chain.

• Updated Plan
  └ □ Resolve token metadata and strict pricing inputs
    □ Derive the signer address from PRIVATE_KEY
    □ Prepare and validate the limit-order bundle
    □ Submit the transaction and parse OrderCreated
    □ Read the created order status and summarize the outcome

• Called vetrade_ai.list_supported_tokens({})
  └ {"tokens":[...]}

• Ran a local signer derivation with PRIVATE_KEY
  └ {"maker":"0xYourSignerAddress"}

• Called vetrade_ai.prepare_limit_order({...,"maker":"0xYourSignerAddress"})
  └ {"action":"create","bundle":{"rawClauses":[...]}...}

• Called vetrade_ai.validate_swap_bundle({...})
  └ {"success":true,...}

• Ran local preflight checks
  └ {"network":"mainnet","tokenBalanceOk":true,"gasEstimateMethod":"thorClient.gas.estimateGas(clauses, sender, { gasPadding: 0.25 })","gasEstimate":"...","vthoBalanceOk":true}

• Ran a local VeChain SDK submission script
  └ {"txId":"0x...","receipt":{"reverted":false,...},"orderCreated":{"orderId":"12345"}}

• Called vetrade_ai.get_limit_order_status({"orderId":"12345"})
  └ {"order":{"orderId":"12345",...},"source":"on_chain"}

• Limit order created on VeChain mainnet.

  - Transaction: 0x...
  - Maker: 0xYourSignerAddress
  - Order id: 12345
  - Input: 500 VTHO
  - Minimum output or target price: ...
  - Bundle clauses: ...
  - Validation: success
  - Final order status: OPEN
  - Source: on_chain
  - Warnings: none

Limit order list

Prompt

Using vetrade skills, list my active VeChain limit orders for maker 0xYourWalletAddress with page 1 and pageSize 20, then summarize order status, pagination, source, and warnings.

Result

• I’m using the vetrade-ai skill for a read-only listing flow.

• Updated Plan
  └ □ Request the filtered limit-order list
    □ Summarize Order Status, Pagination, Source, and Warnings

• Called vetrade_ai.list_limit_orders({"maker":"0xYourWalletAddress","status":"ACTIVE","page":1,"pageSize":20})
  └ {"source":"on_chain",...}

• [Final limit-order listing summary goes here.]

Limit order detail

Prompt

Using vetrade skills, show me the full VeChain detail for limit order 14978 and summarize status, amount remaining, fill count, source, and warnings.

Result

• I’m using the vetrade-ai skill for a single-order status lookup.

• Updated Plan
  └ □ Read the on-chain status for the requested order
    □ Summarize Order Status, amount remaining, fill count, source, and warnings

• Called vetrade_ai.get_limit_order_status({"orderId":"14978"})
  └ {"order":{"orderId":"14978",...}}

• [Final limit-order detail summary goes here.]

Limit order cancel

Prompt

Using vetrade skills. Cancel VeChain limit order 14978. My private key is in env PRIVATE_KEY.

Result

• I’m using the vetrade-ai skill for a local limit-order cancellation. I’ll derive the signer from PRIVATE_KEY, prepare and validate the cancellation bundle, submit it locally, then confirm the final order status on-chain.

• Updated Plan
  └ □ Derive the signer address from PRIVATE_KEY
    □ Prepare and validate the cancellation bundle
    □ Submit the transaction locally
    □ Read the final order status and summarize the outcome

• Ran a local signer derivation with PRIVATE_KEY
  └ {"maker":"0xYourSignerAddress"}

• Called vetrade_ai.prepare_limit_order_cancellation({"maker":"0xYourSignerAddress","orderId":"14978"})
  └ {"action":"cancel","bundle":{"rawClauses":[...]}...}

• Called vetrade_ai.validate_swap_bundle({...})
  └ {"success":true,...}

• Ran local preflight checks
  └ {"network":"mainnet","gasEstimateMethod":"thorClient.gas.estimateGas(clauses, sender, { gasPadding: 0.25 })","gasEstimate":"...","vthoBalanceOk":true}

• Ran a local VeChain SDK submission script
  └ {"txId":"0x...","receipt":{"reverted":false,...}}

• Called vetrade_ai.get_limit_order_status({"orderId":"14978"})
  └ {"order":{"orderId":"14978","status":"CANCELLED",...},"source":"on_chain"}

• Limit order cancelled on VeChain mainnet.

  - Transaction: 0x...
  - Order id: 14978
  - Maker: 0xYourSignerAddress
  - Bundle clauses: ...
  - Validation: success
  - Final order status: CANCELLED
  - Source: on_chain
  - Warnings: none

Output requirements

  • quote summary
  • minimum output
  • route summary
  • limit-order creation or cancellation summary when applicable
  • order status, pagination, and source when a limit-order read is requested
  • allowance requirements when present
  • validation result when a bundle is returned
  • tx id and receipt outcome when local execution happened
  • actual settlement for swaps
  • final order status and created orderId for limit-order create or cancel flows
  • warnings

Advanced execution references

The default happy path now runs inside the VeTrade skill itself with PRIVATE_KEY. Keep these references only for non-default environments:

  • vechain-core from vechain/vechain-ai-skills for custom SDK flows, fee delegation, or advanced execution tuning
  • vechain-kit from vechain/vechain-ai-skills for web wallet flows and useSendTransaction
  • vechain-react-native-dev from vechain/vechain-ai-skills for React Native wallet signing

Safety guidance

  • Use 0xYourPrivateKey placeholders only in docs, prompts, and examples.
  • Never paste a real private key into repository docs or skill metadata.
  • Treat any key that was exposed in prompts, logs, or chat history as compromised and rotate it after testing.

Execution boundary

  • The public VeTrade MCP server can quote, prepare, validate, and read order status.
  • The public VeTrade MCP server does not sign or execute.
  • The VeTrade Codex skill may sign and submit locally with PRIVATE_KEY.
  • Do not describe local skill execution as a remote MCP capability.