raresats.net API
Offers API View as Markdown

Prepare to accept an offer

POST/api/market/offers/{id}/accept/prepare

Step 1 of accepting, for the UTXO's current holder only: checks the offer is active and the UTXO unspent at the same address and value, and returns the offer transaction with input 0 (your UTXO) ready for your wallet. It carries no bidder signature.

Path parameters #

ParameterTypeRequiredDescription
idstringyesThe offer id (16 hex characters).

Request body #

content-type: application/json

FieldTypeRequiredDescription
seller_addressstringyesThe address that holds the UTXO (the offer's seller_address).
seller_public_keystringyesIts public key, hex (Taproot: the internal key, x-only or compressed; SegWit: compressed).

Example request #

cURL
curl -X POST 'https://raresats.net/api/market/offers/dbf866a1e7e209e7/accept/prepare' \
  -H 'content-type: application/json' \
  -d '{
  "seller_address": "bc1p5cyxnuxmeuwuvkwfem96lqzszd02n6xdcjrs20cac6yqjjwudpxqkedrcr",
  "seller_public_key": "03cc8a4bc64d897bddc5fbc2f670f7a8ba0b386779106cf1223c6fc5d7cd6fc115"
}'
JavaScript
const response = await fetch('https://raresats.net/api/market/offers/dbf866a1e7e209e7/accept/prepare', {
  method: 'POST',
  headers: { 'content-type': 'application/json' },
  body: JSON.stringify({
    "seller_address": "bc1p5cyxnuxmeuwuvkwfem96lqzszd02n6xdcjrs20cac6yqjjwudpxqkedrcr",
    "seller_public_key": "03cc8a4bc64d897bddc5fbc2f670f7a8ba0b386779106cf1223c6fc5d7cd6fc115"
  })
});
const data = await response.json();
Python
import requests

data = requests.post("https://raresats.net/api/market/offers/dbf866a1e7e209e7/accept/prepare", json={
    "seller_address": "bc1p5cyxnuxmeuwuvkwfem96lqzszd02n6xdcjrs20cac6yqjjwudpxqkedrcr",
    "seller_public_key": "03cc8a4bc64d897bddc5fbc2f670f7a8ba0b386779106cf1223c6fc5d7cd6fc115"
}).json()

Response 200 #

FieldTypeDescription
psbtstringThe offer transaction, base64, with input 0 ready for your wallet. It carries no bidder signature (the server adds them).
signarray of objectInput 0, your UTXO: sign it with your wallet's default sighash.
sign[].indexintegerThe input to sign.
sign[].addressstringThe address whose key signs it.
sign[].sighashintegerThe sighash type to sign with, when it is not the default: 131 (0x83, SIGHASH_SINGLE|ANYONECANPAY) for listings. Absent on purchase inputs: sign with the default (SIGHASH_DEFAULT for Taproot, SIGHASH_ALL for SegWit v0).
summaryobjectThe trade you accept.
summary.outpointstringYour UTXO.
summary.valueintegerIts value in sats (it goes to the bidder).
summary.priceintegerWhat you receive, in sats (output 1, to your address).
summary.platform_feeintegerThe bidder's platform fee.
summary.network_feeintegerThe network fee, paid by the bidder.
summary.totalintegerWhat the bidder pays.
summary.vsizeintegerEstimated virtual size.
summary.fee_ratenumbersat/vB, fixed by the bidder. If it confirms slowly, you can speed it up by spending output 1 (CPFP).
summary.unit_pricenumber(price - value) / count.
summary.rowstringThe UTXO's own row.
summary.countintegerSats of row in the UTXO.
summary.bidder_ordinals_addressstringWhere the UTXO goes.
summary.listing_idstring | nullYour live listing of the UTXO, if any: accepting sells it (sold once confirmed).
Response
{
  "psbt": "cHNidP8BAP0fAQIAAAACfxBUfmD8FgvLWC+rhhI7HaW1ncmmlqpbSg8h3N/usyQAAAAAAP3///9Bihr4H2G1iZuygx3BHzwLSWfyqpoJAv/W0tpPJYLJAQAAAAAA/f///wUQJwAAAAAAACJRIKgvKZRNZbhq5rXlzHXilOrWxZORoe3F4BbjSYxn/Hu7sK0BAAAAAAAiUSCmCGnw288dxlnJzsuvgFATXqnozcSHBT8dxogJSdxoTL4KAAAAAAAAIlEgrfKcXTOb9Ymo27aSDRsOplytPApoV4riNE46JGW7F/AvJxUAAAAAACJRIKgvKZRNZbhq5rXlzHXilOrWxZORoe3F4BbjSYxn/Hu7AAAAAAAAAAAOagxyYXJlc2F0cy5uZXQAAAAAAAEBKxAnAAAAAAAAIlEgpghp8NvPHcZZyc7Lr4BQE16p6M3EhwU/HcaICUncaEwBFyDMikvGTYl73cX7wvZw96i6CzhneRBs8SI8b8XXzW/BFQABAStg4xYAAAAAACJRIKgvKZRNZbhq5rXlzHXilOrWxZORoe3F4BbjSYxn/Hu7AAAAAAAA",
  "sign": [
    {
      "index": 0,
      "address": "bc1p5cyxnuxmeuwuvkwfem96lqzszd02n6xdcjrs20cac6yqjjwudpxqkedrcr"
    }
  ],
  "summary": {
    "outpoint": "24b3eedfdc210f4a5baa96a6c99db5a51d3b1286ab2f58cb0b16fc607e54107f:0",
    "value": 10000,
    "price": 110000,
    "platform_fee": 2750,
    "network_fee": 963,
    "total": 113713,
    "vsize": 321,
    "fee_rate": 3,
    "unit_price": 100000,
    "row": "decasat_alpha",
    "count": 1,
    "bidder_ordinals_address": "bc1p4qhjn9zdvkux4e44uhx8tc55attvtyu358kutcqkudyccelu0was9fqzwh",
    "listing_id": "5e1cb930f43354c3"
  }
}

Errors #

{error, code}; see Errors for every code.

StatusCodeMeaning
400bad_addressAn address is not a mainnet address (or not one at all).
400bad_jsonThe body is not valid JSON.
400bad_public_keyA public key is not hex, or not a valid secp256k1 key of the right size.
400bad_requestThe body is not a JSON object, or the engine refused a malformed request (e.g. a purchase submitted without its signed setup PSBT).
403cross_originA POST from a browser on another site (a foreign Origin, or sec-fetch-site: cross-site). Server-side clients send no Origin and are not affected.
404not_foundNo such listing or offer. In chat: no such message. A display name to remove that does not exist.
405method_not_allowedWrong method for the route; the allow header lists the right ones.
409changedThe UTXO's value is not what the PSBT says, or (wallet tools) a UTXO, its sats or the transaction being replaced changed since prepare: prepare again.
409config_changedThe marketplace settings changed since this purchase or transfer was prepared (prepare it again), or since this offer was made (it is now invalid, reason config_changed).
409expiredThe prepared purchase, offer or transfer expired, or the offer itself has: prepare it again.
409not_activeA listing (or offer) is not active: being bought (or accepted), sold, cancelled, moved, expired or invalid. Carries id and status.
409spentThe UTXO (or a listing's UTXO) is spent or does not exist.
413too_largeThe body is over 256 KiB.
415not_jsonA POST without content-type: application/json.
422key_mismatchThe public key does not control the address.
422legacy_addressA legacy (P2PKH, 1…) address: use Taproot or SegWit.
422not_ownerThe UTXO does not belong to the seller address, or (wallet tools) to the owner's addresses, or the transfer was made by another wallet.
422pubkey_mismatchThe trade engine found the public key is not the address's key.
422unsupported_addressAn address type the marketplace does not trade (only Taproot, native SegWit and nested SegWit).
422unsupported_scriptThe trade engine met a script type it does not support.
429rate_limitedOver 30 POSTs a minute from your IPv4 address or IPv6 /64 (in chat, counted per IPv4 address or IPv6 /64: 30 writes and 20 login nonces a minute, 20 sign-ins and 10 display-name changes an hour; one message every 3 s and 20 a minute per address); wait retry-after seconds. With the AI moderation on, at most 6 messages and names a minute are checked per address and per IPv4 address or IPv6 /48.
500internalA server bug. Report it.
503bitcoind_unavailablebitcoind is not available.
503engine_unavailableThe trade engine is not available.
503fork_unavailableThe rare-sat index is not available.
503market_unavailableThe marketplace is closed right now (its backends disagree on the network, or are unreachable).
503oracle_unavailableThe ord oracle is not available.
Error (422)
{
  "error": "24b3eedfdc210f4a5baa96a6c99db5a51d3b1286ab2f58cb0b16fc607e54107f:0 is not held by bc1p4qhjn9zdvkux4e44uhx8tc55attvtyu358kutcqkudyccelu0was9fqzwh: only its holder can accept",
  "code": "not_owner",
  "outpoint": "24b3eedfdc210f4a5baa96a6c99db5a51d3b1286ab2f58cb0b16fc607e54107f:0"
}

Then sign input 0 with your wallet's default sighash and accept. You receive price at the address that holds the UTXO (output 1); the bidder pays the platform fee and the network fee.