Skip to main content
Paper trading lets you simulate stock trades with virtual money. Create an account with a starting balance, buy and sell securities, and track your portfolio — all without risking real capital.

How it works

Paper trading uses Yoshi’s action approval model. When you create an account or place a trade, the API returns a pending action that must be approved before execution. This safety layer prevents accidental trades.
Create action → Pending → Approved → Executed
                   ↘ Rejected

Create a paper trading account

import Yoshi from "@yoshi-ai/sdk";

const yoshi = new Yoshi();

const result = await yoshi.paperTrading.accounts.create({
  name: "Tech Portfolio",
  starting_cash_balance: "50000", // $50,000
});

console.log("Action ID:", result.action_id);
console.log("Status:", result.status);
console.log("Approve at:", result.approval_url);
The response includes an approval_url — open it in your Yoshi dashboard to approve the account creation.

Place a trade

Buy stock by share quantity or dollar amount:
// Buy 10 shares of AAPL
const trade = await yoshi.paperTrading.accounts.trades.create("acc_paper123", {
  symbol: "AAPL",
  side: "buy",
  quantity: 10,
});

// Or buy $5,000 worth of AAPL
const notionalTrade = await yoshi.paperTrading.accounts.trades.create(
  "acc_paper123",
  {
    symbol: "AAPL",
    side: "buy",
    notional: 5000,
  },
);

console.log("Approve trade:", trade.approval_url);
Provide either quantity or notional, not both. The API returns a validation error if you include both fields.

Use idempotency keys

Prevent duplicate trades when retrying failed requests:
curl -X POST https://api.yoshi.ai/paper-trading/accounts/acc_paper123/trades \
  -H "Authorization: Bearer yoshi_YOUR_KEY" \
  -H "Content-Type: application/json" \
  -H "Idempotency-Key: trade-aapl-2026-04-10-001" \
  -d '{"symbol": "AAPL", "side": "buy", "quantity": 10}'
If you send the same Idempotency-Key again, the API returns the cached response instead of creating a duplicate trade. See Idempotency for details.

Check the approval status

Poll the approval endpoint to track whether the action was approved:
const status = await yoshi.approvals.retrieve("thread_abc123");

console.log("Status:", status.status); // "pending", "approved", "rejected", "executed"

View your portfolio

List current holdings and trade history:
// Current holdings
const holdings = await yoshi.paperTrading.accounts.holdings.list("acc_paper123");

for (const h of holdings.holdings) {
  console.log(`${h.symbol}: ${h.quantity} shares @ $${h.institution_price}`);
}

// Trade history
for await (const trade of yoshi.paperTrading.accounts.trades.list("acc_paper123")) {
  console.log(`${trade.type} ${trade.symbol}: ${trade.quantity} @ $${trade.price}`);
}

What’s next

Actions & Approvals

Understand the full approval lifecycle.

Idempotency

Prevent duplicate operations.
Last modified on April 17, 2026