Appearance
Integration by Hash Name (API Flow)
A two-step API flow for merchants who already know which items the user wants to deposit (by market hash name) and don't need to fetch the user's full Steam inventory upfront.
This is the most flexible deposit flow — useful when you maintain your own item catalog or accept deposits driven by your own UX (e.g. a "deposit this item" button on your platform).
When to use this flow
- You already know the item names (from your own listings, marketplace, or saved cart)
- You want to show a confirmed price quote to the user before they commit
- You want price-drop protection via per-item
min_price - You don't want to fetch the user's full Steam inventory just to price a few specific items
- You have (or can obtain) the Steam
asset_idfor each item — this flow still requires asset IDs to identify the physical items for the trade offer
For other flows, see:
- Redirect Flow — full hosted UI
- Iframe Flow — embedded UI
- API-Only Flow — fetch full Steam inventory + select by
asset_id
Flow Overview
Your Platform Skinslink
───────────── ─────────
│ │
│ 1. POST /merchant/get-prices │
│ { game, marketHashNames } │
│ ─────────────────────────────────────────► │
│ │
│ { id, total, sum, items[] } │
│ ◄───────────────────────────────────────── │
│ │
│ Show quote to user (5-minute window) │
│ User confirms │
│ │
│ 2. POST /merchant/create-deposit-by-hash-name
│ { id, merchant_tx_id, game, partner, │
│ token, items[{asset_id, name, │
│ min_price}] } │
│ ─────────────────────────────────────────► │
│ │
│ { id, status, trade_offer_id, ... } │
│ ◄───────────────────────────────────────── │
│ │
│ 3. User accepts Steam trade offer │
│ │
│ 4. Webhook: trade status │
│ ◄───────────────────────────────────────── │Step 1: Get a Price Quote
Call Get Prices with the game code and the list of item market hash names you want to price.
bash
curl -X POST https://api.skinslink.com/api/v1/merchant/get-prices \
-H "X-Api-Key: your-api-key" \
-H "Content-Type: application/json" \
-d '{
"game": "csgo",
"marketHashNames": [
"AK-47 | Redline (Field-Tested)",
"AWP | Asiimov (Field-Tested)"
]
}'The response contains a trade id (valid for 5 minutes), the total sum, and per-item prices:
json
{
"data": {
"id": 742,
"total": 2,
"sum": 45.50,
"items": [
{ "name": "AK-47 | Redline (Field-Tested)", "price": 22.75, "originalPrice": 23.10 },
{ "name": "AWP | Asiimov (Field-Tested)", "price": 22.75, "originalPrice": 23.10 }
]
}
}Show the quote to the user. Save the id — you'll need it for step 2.
Price-only quotes
If you just want to display a price without creating a trade record (e.g. on a product page), pass no_deposit_intent: true. No id will be returned, and no trade will be created.
5-minute window
The 5-minute clock starts the moment get-prices creates the trade record (at the time of its response). If the user takes longer to confirm, call get-prices again to get a fresh id.
Step 2: Commit the Deposit
Once the user confirms, you need:
- The trade
idfrom step 1 - A
merchant_tx_idunique to this transaction on your side - The
gamecode (same as used in step 1) - The user's Steam trade URL (
partner+token) - For each item: its Steam
asset_id, its market hashname, and optionally amin_pricefloor - Optionally, a
result_urlto receive webhook notifications for this specific deposit (overrides your merchant-level webhook URL)
Where do asset_ids come from?
You need the asset_id for each Steam item the user is depositing. You can get this from the user's Steam inventory (via Steam's inventory API or a cached copy in your backend). The hash-name flow lets you skip the pricing inventory call — but Steam still needs asset_id to identify which physical items to transfer.
Call Create Deposit by Hash Name:
bash
curl -X POST https://api.skinslink.com/api/v1/merchant/create-deposit-by-hash-name \
-H "X-Api-Key: your-api-key" \
-H "Content-Type: application/json" \
-d '{
"id": 742,
"merchant_tx_id": "order-9999",
"game": "csgo",
"partner": 123456789,
"token": "AbCdEfGh",
"items": [
{
"asset_id": "38029384123",
"name": "AK-47 | Redline (Field-Tested)",
"min_price": 22.50
},
{
"asset_id": "38029384124",
"name": "AWP | Asiimov (Field-Tested)",
"min_price": 22.50
}
]
}'The response contains the bot's Steam ID, trade offer ID, and expiry timestamp. Display this so the user can find and accept the offer in Steam.
Setting min_price
min_price protects you from price drift inside the 5-minute window. A safe default is the price you quoted to the user, possibly minus 1–2% for a small tolerance. If the live price drops below min_price for any item, the request fails with HTTP 400 and error message item_specified_price_not_found — you can prompt the user to refresh the quote. Values ≤ 0 are silently ignored (no protection applied).
Step 3: User Accepts the Trade Offer
The user opens Steam and accepts the trade offer from the Skinslink bot. If they don't accept before trade_offer_expiry_at, the offer is automatically canceled.
Step 4: Track Deposit Status
Option A: Webhooks (recommended)
Skinslink POSTs to your result_url (or merchant webhook URL) whenever the trade transitions to hold, completed, failed, canceled, or reverted.
→ See Webhooks for payload format and signature verification.
Option B: Poll the status endpoint
Use Deposit Status with either the trade id or your merchant_tx_id.
Comparison with the API-Only Flow
| Aspect | API-Only Flow | Hash-Name Flow |
|---|---|---|
| Item lookup | Steam inventory (partner+token) | Market hash name |
| Price check before commit | No | Yes (5-minute quote) |
min_price protection | No | Yes, per item |
merchant_tx_id set at | create-deposit | create-deposit-by-hash-name (step 2) |
| Best for | Letting the user pick from their full inventory | You already know which items |
Errors
Common error scenarios:
inventory_reload(validation error oninventory) — the 5-minute quote window expired. Callget-pricesagain.item_specified_price_not_found— HTTP 400 returned when an item's current price fell below yourmin_price. Refresh the quote and retry.provider_unavailable— the upstream provider rejected the trade, timed out, or an internal error occurred before reaching the provider. Retry after a short delay.- Duplicate
merchant_tx_id—409 already exist error. Use a fresh ID.
→ Full error reference: Errors.
