curl --request POST \
--url https://arena-predictions.com/api/v1/portfolio/orders \
--header 'Authorization: Bearer <token>' \
--header 'Content-Type: application/json' \
--data '
{
"action": "buy",
"type": "limit",
"instrumentId": "ins_0123456789AB",
"side": "yes",
"count": 10,
"limitPriceCents": 40,
"timeInForce": "gtc",
"idempotencyKey": "1b4e28ba-2fa1-41d2-883f-0016d3cca427"
}
'import requests
url = "https://arena-predictions.com/api/v1/portfolio/orders"
payload = {
"action": "buy",
"type": "limit",
"instrumentId": "ins_0123456789AB",
"side": "yes",
"count": 10,
"limitPriceCents": 40,
"timeInForce": "gtc",
"idempotencyKey": "1b4e28ba-2fa1-41d2-883f-0016d3cca427"
}
headers = {
"Authorization": "Bearer <token>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {Authorization: 'Bearer <token>', 'Content-Type': 'application/json'},
body: JSON.stringify({
action: 'buy',
type: 'limit',
instrumentId: 'ins_0123456789AB',
side: 'yes',
count: 10,
limitPriceCents: 40,
timeInForce: 'gtc',
idempotencyKey: '1b4e28ba-2fa1-41d2-883f-0016d3cca427'
})
};
fetch('https://arena-predictions.com/api/v1/portfolio/orders', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));{
"status": "executed",
"action": "buy",
"type": "market",
"idempotencyKey": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"replayed": true,
"originalCreatedAt": "2023-11-07T05:31:56Z",
"order": {
"orderId": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"action": "buy",
"instrumentId": "<string>",
"instrumentLabel": "<string>",
"instrumentSide": "yes",
"orderSide": "yes",
"contracts": 123,
"filledContracts": 123,
"remainingContracts": 123,
"limitCents": 123,
"holdDollars": 123,
"timeInForce": "<string>",
"expiresAt": "2023-11-07T05:31:56Z",
"status": "<string>",
"createdAt": "2023-11-07T05:31:56Z",
"type": "limit",
"cancelReason": "<string>",
"tradeId": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"statedProbPct": 123,
"placedVia": "<string>",
"placedPrivate": true,
"marketTicker": "<string>",
"fillPriceCents": 123
},
"trade": {
"tradeId": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"instrumentId": "<string>",
"instrumentLabel": "<string>",
"instrumentSide": "yes",
"boughtSide": "yes",
"contracts": 123,
"costDollars": 123,
"statedProbPct": 123,
"placedVia": "<string>",
"placedPrivate": true,
"parlayId": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"fillVenue": "<string>",
"openedAt": "2023-11-07T05:31:56Z",
"status": "open",
"closedAt": "2023-11-07T05:31:56Z",
"closeReason": "<string>",
"pnlDollars": 123,
"resolvedOutcome": "yes",
"marketTicker": "<string>",
"entryCents": 123
},
"fillVenue": "kalshi",
"mode": "paper",
"venueData": true,
"fills": [
{
"venue": "kalshi",
"contracts": 123,
"priceCents": 50
}
],
"fillPriceCents": 123,
"organization": {
"id": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"slug": "<string>"
}
}{
"status": "executed",
"action": "buy",
"type": "market",
"idempotencyKey": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"replayed": true,
"originalCreatedAt": "2023-11-07T05:31:56Z",
"order": {
"orderId": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"action": "buy",
"instrumentId": "<string>",
"instrumentLabel": "<string>",
"instrumentSide": "yes",
"orderSide": "yes",
"contracts": 123,
"filledContracts": 123,
"remainingContracts": 123,
"limitCents": 123,
"holdDollars": 123,
"timeInForce": "<string>",
"expiresAt": "2023-11-07T05:31:56Z",
"status": "<string>",
"createdAt": "2023-11-07T05:31:56Z",
"type": "limit",
"cancelReason": "<string>",
"tradeId": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"statedProbPct": 123,
"placedVia": "<string>",
"placedPrivate": true,
"marketTicker": "<string>",
"fillPriceCents": 123
},
"trade": {
"tradeId": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"instrumentId": "<string>",
"instrumentLabel": "<string>",
"instrumentSide": "yes",
"boughtSide": "yes",
"contracts": 123,
"costDollars": 123,
"statedProbPct": 123,
"placedVia": "<string>",
"placedPrivate": true,
"parlayId": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"fillVenue": "<string>",
"openedAt": "2023-11-07T05:31:56Z",
"status": "open",
"closedAt": "2023-11-07T05:31:56Z",
"closeReason": "<string>",
"pnlDollars": 123,
"resolvedOutcome": "yes",
"marketTicker": "<string>",
"entryCents": 123
},
"fillVenue": "kalshi",
"mode": "paper",
"venueData": true,
"fills": [
{
"venue": "kalshi",
"contracts": 123,
"priceCents": 50
}
],
"fillPriceCents": 123,
"organization": {
"id": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"slug": "<string>"
}
}{
"error": {
"code": "invalid_request",
"message": "<string>",
"retryAfterSeconds": 2
}
}{
"error": {
"code": "invalid_request",
"message": "<string>",
"retryAfterSeconds": 2
}
}{
"error": {
"code": "invalid_request",
"message": "<string>",
"retryAfterSeconds": 2
}
}{
"error": {
"code": "invalid_request",
"message": "<string>",
"retryAfterSeconds": 2
}
}{
"error": {
"code": "invalid_request",
"message": "<string>",
"retryAfterSeconds": 2
}
}{
"error": {
"code": "invalid_request",
"message": "<string>",
"retryAfterSeconds": 2
}
}{
"error": {
"code": "invalid_request",
"message": "<string>",
"retryAfterSeconds": 2
}
}{
"error": {
"code": "invalid_request",
"message": "<string>",
"retryAfterSeconds": 2
}
}Place a paper order
Places an order for the key owner. The default is a paper order, as the CLI and the MCP server do: nothing is sent to Kalshi or any venue. execution kalshi sends a live Kalshi order (scope trade:write:kalshi) through the live door and does not touch the paper book. execution poly-intl sends a live Polymarket International order (scope trade:write:poly-intl) and refuses a US visitor. Polymarket US is not offered. Send X-Arena-Org to place a paper order on that organization’s paper sandbox; without the header the paper order is on the personal account. An unknown or forbidden organization places nothing. A market order fills now at the live price or is refused. A limit order fills at limitPriceCents or better, rests until it fills, is canceled or expires (gtc), or is canceled at once when it does not fill (ioc, fok). Opening a position needs Arena Basic. Every paper order counts against the hard trade limits (per key 10 new orders a minute and 50 a day, 20 sells and cancels a minute; per account 20, 100 and 40), which are always enforced. No ticker, title or price in the paper answer while the venue-data switch is off.
curl --request POST \
--url https://arena-predictions.com/api/v1/portfolio/orders \
--header 'Authorization: Bearer <token>' \
--header 'Content-Type: application/json' \
--data '
{
"action": "buy",
"type": "limit",
"instrumentId": "ins_0123456789AB",
"side": "yes",
"count": 10,
"limitPriceCents": 40,
"timeInForce": "gtc",
"idempotencyKey": "1b4e28ba-2fa1-41d2-883f-0016d3cca427"
}
'import requests
url = "https://arena-predictions.com/api/v1/portfolio/orders"
payload = {
"action": "buy",
"type": "limit",
"instrumentId": "ins_0123456789AB",
"side": "yes",
"count": 10,
"limitPriceCents": 40,
"timeInForce": "gtc",
"idempotencyKey": "1b4e28ba-2fa1-41d2-883f-0016d3cca427"
}
headers = {
"Authorization": "Bearer <token>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {Authorization: 'Bearer <token>', 'Content-Type': 'application/json'},
body: JSON.stringify({
action: 'buy',
type: 'limit',
instrumentId: 'ins_0123456789AB',
side: 'yes',
count: 10,
limitPriceCents: 40,
timeInForce: 'gtc',
idempotencyKey: '1b4e28ba-2fa1-41d2-883f-0016d3cca427'
})
};
fetch('https://arena-predictions.com/api/v1/portfolio/orders', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));{
"status": "executed",
"action": "buy",
"type": "market",
"idempotencyKey": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"replayed": true,
"originalCreatedAt": "2023-11-07T05:31:56Z",
"order": {
"orderId": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"action": "buy",
"instrumentId": "<string>",
"instrumentLabel": "<string>",
"instrumentSide": "yes",
"orderSide": "yes",
"contracts": 123,
"filledContracts": 123,
"remainingContracts": 123,
"limitCents": 123,
"holdDollars": 123,
"timeInForce": "<string>",
"expiresAt": "2023-11-07T05:31:56Z",
"status": "<string>",
"createdAt": "2023-11-07T05:31:56Z",
"type": "limit",
"cancelReason": "<string>",
"tradeId": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"statedProbPct": 123,
"placedVia": "<string>",
"placedPrivate": true,
"marketTicker": "<string>",
"fillPriceCents": 123
},
"trade": {
"tradeId": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"instrumentId": "<string>",
"instrumentLabel": "<string>",
"instrumentSide": "yes",
"boughtSide": "yes",
"contracts": 123,
"costDollars": 123,
"statedProbPct": 123,
"placedVia": "<string>",
"placedPrivate": true,
"parlayId": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"fillVenue": "<string>",
"openedAt": "2023-11-07T05:31:56Z",
"status": "open",
"closedAt": "2023-11-07T05:31:56Z",
"closeReason": "<string>",
"pnlDollars": 123,
"resolvedOutcome": "yes",
"marketTicker": "<string>",
"entryCents": 123
},
"fillVenue": "kalshi",
"mode": "paper",
"venueData": true,
"fills": [
{
"venue": "kalshi",
"contracts": 123,
"priceCents": 50
}
],
"fillPriceCents": 123,
"organization": {
"id": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"slug": "<string>"
}
}{
"status": "executed",
"action": "buy",
"type": "market",
"idempotencyKey": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"replayed": true,
"originalCreatedAt": "2023-11-07T05:31:56Z",
"order": {
"orderId": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"action": "buy",
"instrumentId": "<string>",
"instrumentLabel": "<string>",
"instrumentSide": "yes",
"orderSide": "yes",
"contracts": 123,
"filledContracts": 123,
"remainingContracts": 123,
"limitCents": 123,
"holdDollars": 123,
"timeInForce": "<string>",
"expiresAt": "2023-11-07T05:31:56Z",
"status": "<string>",
"createdAt": "2023-11-07T05:31:56Z",
"type": "limit",
"cancelReason": "<string>",
"tradeId": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"statedProbPct": 123,
"placedVia": "<string>",
"placedPrivate": true,
"marketTicker": "<string>",
"fillPriceCents": 123
},
"trade": {
"tradeId": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"instrumentId": "<string>",
"instrumentLabel": "<string>",
"instrumentSide": "yes",
"boughtSide": "yes",
"contracts": 123,
"costDollars": 123,
"statedProbPct": 123,
"placedVia": "<string>",
"placedPrivate": true,
"parlayId": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"fillVenue": "<string>",
"openedAt": "2023-11-07T05:31:56Z",
"status": "open",
"closedAt": "2023-11-07T05:31:56Z",
"closeReason": "<string>",
"pnlDollars": 123,
"resolvedOutcome": "yes",
"marketTicker": "<string>",
"entryCents": 123
},
"fillVenue": "kalshi",
"mode": "paper",
"venueData": true,
"fills": [
{
"venue": "kalshi",
"contracts": 123,
"priceCents": 50
}
],
"fillPriceCents": 123,
"organization": {
"id": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"slug": "<string>"
}
}{
"error": {
"code": "invalid_request",
"message": "<string>",
"retryAfterSeconds": 2
}
}{
"error": {
"code": "invalid_request",
"message": "<string>",
"retryAfterSeconds": 2
}
}{
"error": {
"code": "invalid_request",
"message": "<string>",
"retryAfterSeconds": 2
}
}{
"error": {
"code": "invalid_request",
"message": "<string>",
"retryAfterSeconds": 2
}
}{
"error": {
"code": "invalid_request",
"message": "<string>",
"retryAfterSeconds": 2
}
}{
"error": {
"code": "invalid_request",
"message": "<string>",
"retryAfterSeconds": 2
}
}{
"error": {
"code": "invalid_request",
"message": "<string>",
"retryAfterSeconds": 2
}
}{
"error": {
"code": "invalid_request",
"message": "<string>",
"retryAfterSeconds": 2
}
}Authorizations
Authorization: Bearer arena_sk_... (the x-arena-key header is accepted too). Keys are made in Settings (https://arena-predictions.com/settings#api-keys) or with arena keys create, shown once, stored hashed.
Headers
Organization id. When present, this call uses that organization's paper sandbox. When absent, the key owner's personal paper account. A value that is not an organization id is 400 invalid_request. An unknown organization is 404 organization_not_found and one this key cannot use is 403 organization_forbidden. The personal account is never the fallback. Paper only. This header does not select a Combine evaluation account.
63Body
A buy names instrumentId or ticker, side and count. A sell names tradeId and covers the whole open position. A limit order adds limitPriceCents. Unknown fields are refused (400), so a typo never changes an order.
market: fills now at the live price or is refused. limit: fills at limitPriceCents or better, or rests (gtc), or is canceled (ioc, fok).
market, limit One per order. The same key again answers the stored order with replayed: true and places nothing; the same key with a different order is 409 idempotency_key_reused. Retry with the same key after a timeout or a 503.
buy, sell Kalshi's name for idempotencyKey. Send one of the two.
Buy: the Arena instrument; side is the instrument's side. It must list on one live Kalshi market (409 no_tradable_listing otherwise).
^ins_[0-9A-HJKMNP-TV-Z]{12}$Buy: a Kalshi market ticker instead of instrumentId; side is the market's side. Never echoed back while the venue-data switch is off.
Buy: the side to buy.
yes, no Buy: contracts. Your paper balance is the limit.
1 <= x <= 1000000000Sell: the open position (GET /portfolio).
Limit: your price for the side you trade, in cents (a percent).
1 <= x <= 99gtc, ioc, fok, good_till_canceled, immediate_or_cancel, fill_or_kill gtc only: when the order stops resting. At most 365 days out.
Market buy: refuse to fill above this (409 price_moved, nothing placed).
1 <= x <= 99Market sell: refuse to sell below this (409 price_moved, nothing sold).
1 <= x <= 99best: a fill may be priced at Novig's or Polymarket's price when it passes every check. Omitted: Kalshi's.
kalshi, best Buy: your probability for the side. Never changes the fill; scored on /eval. Paper only.
1 <= x <= 99paper (default) uses the paper book and trade:write. kalshi sends a live Kalshi order and needs trade:write:kalshi. poly-intl sends a live Polymarket International order and needs trade:write:poly-intl. Polymarket US is not a value.
paper, kalshi, poly-intl Live only. Default create.
create, cancel, amend Live cancel or amend: the Kalshi order id.
Live: the price of the side, in cents.
1 <= x <= 99Live amend: the new price of the side.
1 <= x <= 99Live amend: the new contract count.
x >= 1Response
A replay: this idempotencyKey was used before for the same order. Nothing new was placed.
canceled: an ioc or fok that did not fill. Nothing was spent.
executed, resting, canceled buy, sell market, limit True when this idempotencyKey was used before: the stored order, nothing new placed.
On a replay: when the order was first placed.
The limit order. Null for a market order, which is a fill and not an order.
Show child attributes
Show child attributes
The position opened (buy) or closed (sell). Null while resting or canceled.
Show child attributes
Show child attributes
Where the fill was priced. Paper only: nothing is sent there. The first leg when the ticket split.
kalshi, novig, polymarket, null "paper"Present when route best split one ticket across venues. priceCents is omitted while venue data is off.
Show child attributes
Show child attributes
Only while the venue-data switch is on.
Present when X-Arena-Org selected an organization sandbox. Absent on the personal account.
Show child attributes
Show child attributes