player requests a withdrawal
your backend checks the player’s entitlement and saves a unique withdrawal record. the case result and player ledger belong to your application.
turn a player’s withdrawal into a steam delivery. source the skin from csboard’s catalog, buy it for their trade url and track the order through your backend.
your backend checks the player’s entitlement and saves a unique withdrawal record. the case result and player ledger belong to your application.
read GET /v1/listings?appId=730. match the exact skin and wear, then inspect price_usd, delivery and tradable_at before offering a delivery estimate.
send the listing id, recipient’s trade-url partner and token, a price ceiling and your saved custom_id to POST /v1/market/buy. keep the API key on your server.
store data.purchase_id from the purchase response. reconcile by your custom_id using GET /v1/orders/info and verified webhooks. a purchase being accepted is not proof that the player has received the skin.
compare the exact rewards your players can withdraw before building the purchase flow. the price list is a starting snapshot for commercial evaluation; a live listing determines the item, asking price and delivery state available now.
this read-only request finds the regular field-tested neon revolution. name matches the complete market hash name, case-insensitively; search is a broader text search. keep wear, StatTrak™ and Souvenir aligned with the reward you promised.
read items and continue with next_cursor when present. listing availability is not a reservation. for doppler rewards, inspect doppler_phase as well: matching the name alone does not select a particular phase.
curl --get https://csboard.com/v1/listings \
-H "Authorization: Bearer $CSBOARD_API_KEY" \
--data-urlencode "appId=730" \
--data-urlencode "name=AK-47 | Neon Revolution (Field-Tested)" \
--data-urlencode "stat_trak=exclude" \
--data-urlencode "souvenir=exclude" \
--data-urlencode "sort=price_asc" \
--data-urlencode "limit=20" | what you find | commercial decision |
|---|---|
| matching listings | compare price_usd, delivery and tradable_at. decide which delivery states your product accepts before showing the player a withdrawal option. |
| only locked items | show the applicable wait or keep that reward unavailable for immediate withdrawal. a low price is not evidence of immediate delivery. |
| no matching listings | keep an explicit unavailable state. do not silently replace the wear, StatTrak status or skin; agree any alternative with the player. |
for a supply discussion, include a representative reward list, expected withdrawal volume and acceptable delivery windows in your access request. commercial terms are agreed for your account; this sample is not a price or stock guarantee.
this request spends real settled balance when used with a trading-enabled key and valid inputs. replace the placeholders with a current listing and the recipient’s steam trade-url fields.
the API server is https://csboard.com/v1. the documentation lives at api.csboard.com. append paths such as /market/buy to the server URL once.
curl https://csboard.com/v1/market/buy \
-H "Authorization: Bearer $CSBOARD_API_KEY" \
-H "Content-Type: application/json" \
--data '{
"item_ids": ["<live_listing_id>"],
"partner": "<steam_partner_id>",
"token": "<steam_trade_token>",
"max_price_usd": 120.00,
"custom_id": "withdrawal-1042",
"skip_unavailable": false
}' | outcome | what your integration should do |
|---|---|
| purchase accepted | save the order id and track item delivery. do not mark the withdrawal delivered from the purchase response alone. |
| timeout or unknown result | keep the withdrawal pending and look it up by its saved custom_id. the server caches a successful response for up to 24 hours. after expiry, even the same id can start another purchase. if the outcome is unclear, keep reconciling with GET and investigate before sending another buy. |
| 409 conflict | inspect the error code. idempotency_in_progress means the original request may still be processing. respect Retry-After, then look up the saved id. the end of that wait does not confirm success or failure. |
| 402 insufficient funds | check settled balance. keep the player’s withdrawal pending in your own ledger until funding or another explicit resolution. |
| item gone or price changed | check the exact error and reconcile any prior purchase before selecting a replacement. keep max_price_usd as an execution ceiling; obtain approval before changing the promised item. |
| 429 rate limit | respect Retry-After when present and use bounded backoff. avoid a tight retry loop. |
save custom_id before sending the purchase. POST /v1/market/buy returns its identifier as data.purchase_id; order lookups expose it as data[].order_id. if the response never arrived, use your saved custom_id to look up matching orders.
GET /v1/orders/info accepts comma-separated custom_ids, order_ids, or both, up to 200 identifiers in total. it returns matching orders owned by the authenticated account. the example uses one withdrawal id and only reads status.
curl --get https://csboard.com/v1/orders/info \
-H "Authorization: Bearer $CSBOARD_API_KEY" \
--data-urlencode "custom_ids=withdrawal-1042" | lookup result | next step |
|---|---|
| matching order | save its order_id and inspect status and items. finding an order is not delivery confirmation. apply a completed transition to your own ledger at most once. |
{"data":[]} | no matching order is visible to this account yet. the original request may still be unresolved: do not treat this as proof that nothing was purchased or create a new custom_id. |
| multiple matches | preserve every returned order and investigate the correlation. do not silently select one or credit the same player twice. |
| 401, 403, 429 or timeout | a failed lookup does not resolve the purchase outcome. check access for authentication errors; use Retry-After when supplied and bounded backoff for rate limits. keep the withdrawal unresolved until reconciled. |
a read-only node.js example.
download lookup-withdrawal.mjs for Node.js 20+. keep it on your backend. the helper returns matching orders or an unresolved result; it never buys, retries a purchase or credits a player.
network and HTTP errors throw. your application owns bounded retry scheduling, webhook verification and the final delivery decision. the API key stays server-side and must not be added to a browser bundle.
import { lookupWithdrawal } from './lookup-withdrawal.mjs';
const result = await lookupWithdrawal({
customId: 'withdrawal-1042', // your saved withdrawal id
apiKey: process.env.CSBOARD_API_KEY,
});
// inspect result.orders; found does not mean delivered.
// unresolved means keep reconciling, not start a new buy.
download lookup-with-backoff.mjs beside lookup-withdrawal.mjs. this optional wrapper retries only the read-only lookup after HTTP 429, 502, 503 or 504.
the sample makes at most three GET requests with a ten-second timeout per request and thirty seconds of total retry waits. these are example application settings, not CSBoard account limits. Retry-After accepts seconds or an HTTP date; if the server delay exceeds the remaining wait allowance, the helper throws instead of retrying early.
401/403, an empty result, malformed data and network errors do not trigger an automatic retry. keep the withdrawal unresolved and schedule reconciliation in your backend. a successful lookup still does not confirm delivery. this wrapper never repeats a purchase.
import { lookupWithBackoff } from './lookup-with-backoff.mjs';
try {
const result = await lookupWithBackoff({
customId: 'withdrawal-1042',
apiKey: process.env.CSBOARD_API_KEY,
});
// found is not delivered; unresolved stays in your reconciliation queue.
} catch (error) {
// Keep the withdrawal unresolved. Defer the next GET to your job queue.
// Never create another purchase or a new custom_id here.
} listings expose instant, up_to_12h or hold delivery buckets. a locked item waits until it becomes tradable. show the applicable state before the player confirms, and keep it visible while the order is pending.
verify webhook signatures using the current documentation. reconcile missed or duplicate events against your saved order rather than advancing the player ledger twice.
for accounts with instant sell enabled, POST /v1/sell/quotes quotes the user’s CS2 items and POST /v1/sell/orders starts the sale. use its external_id to correlate your deposit.
receiving the Steam trade and settling merchant balance are different events. Steam trade protection applies before settlement. agree commercial terms and your own player-credit policy before launch.
use csboard when your site needs real skin inventory and delivery to a player’s steam account. case results, upgrade outcomes, battle rewards and player balances stay in your application.
start with the downloadable price list to compare a sample of your rewards. use live listings for availability and execution; a downloaded price is not a reserved offer.
support is available 24/7. include your project url and launch stage below so the discussion starts with your integration.
csboard supplies and delivers skins; it does not implement case odds, game outcomes or a player ledger. your application decides the withdrawal entitlement and asks csboard to fulfill the item. partner access and the proposed use case are reviewed before activation.
you can source from live listings when a player requests delivery. availability and prices can change, so your product still needs a policy for unavailable items. API purchases require sufficient settled balance.
this example uses CS2. the current OpenAPI also documents appId 570 for Dota 2 and 252490 for Rust on /v1/market/buy, subject to your key’s game permissions. those orders initially return pending. confirm access and game-specific behavior before offering them to players.
start with the OpenAPI specification and documentation index. use the published schemas, keep credentials server-side and test retries without issuing live purchases. the integration prompt provides the entry points.
tell us about your case site, expected volume and launch stage. we will discuss access and commercial terms before activation.
or write directly:
read the docs