Cardiv
Market maker programme

Placing and cancelling orders

The three calls that place an order, the three that cancel one, and the rules that catch people out.

Placing an order takes three steps: prepare with Cardiv, sign locally, submit to Calden. Cancelling takes the same three.

Prepare

POST /orders, measured at 9 to 14 seconds.

FieldRequired
pairyesFrom GET /pairs, verbatim
sideyesBUY commits the quote token, SELL commits the base
typeyesLIMIT or MARKET
pricefor LIMITQuote per unit of base, decimal string, at most 10 decimal places. Longer values are rejected, not rounded.
quantityyesBase units, decimal string. price times quantity must meet the pair's minQuoteAmount.
clientOrderIdrecommendedMust start with your account's prefix, at most 120 characters. It is the idempotency key.
{ "pair": "CBTC/cETH", "side": "SELL", "type": "LIMIT",
  "price": "40", "quantity": "0.00002", "clientOrderId": "acme-q1-ask" }

A 202 comes back with nothing on the book. An abandoned prepare expires with no funds committed.

Response field
order.providerFeeAmountAlways "0" for a registered market maker
order.status, order.contractIdnull until the transaction commits
signing.preparedTransactionHashThe value to sign
signing.hashingSchemeVersion, signing.commandId, signing.submitTokenEchoed verbatim in the submission body
signing.submitUrlAbsolute URL on the Calden host

Always set your own clientOrderId. If your client never sees the response, that id is the only way to find out whether the order exists. Preparing again with the same id cannot create a second order: when the first one is already live, the response returns it with no transaction to sign.

Sign

Ed25519 over the raw bytes of the base64-decoded preparedTransactionHash. No re-hashing, no prefix, and not the base64 string itself. Calden verifies the signature against the exact bytes it cached.

Submit

POST {submitUrl}, measured at 18 to 20 seconds.

{
  "partyId":     "<your party>",
  "commandId":   "<signing.commandId>",
  "signature":   "<base64>",
  "publicKey":   "<base64, the key registered for the party>",
  "submitToken": "<signing.submitToken>",
  "prepared": {
    "preparedTransactionHash": "<signing.preparedTransactionHash>",
    "hashingSchemeVersion":    "<signing.hashingSchemeVersion>"
  }
}

A 200 means accepted and dispatched, not resting. Confirmation is asynchronous, and a 200 has been seen for a transaction that never confirmed while the network was degraded. Poll GET /orders/{orderId} until the order reads OPEN, and only then update your own book state. Use that endpoint rather than GET /orders, which refreshes the wallet by default and is far slower. Measured end to end: 32 seconds from submission to a confirmed OPEN.

Set your client timeout on submission to at least 120 seconds. Submissions queue behind a traffic lock and retry consensus timeouts internally, so a short timeout abandons transactions that go on to commit.

If a submission fails, times out, or your client dies before it reads the response, the order may still have committed. GET /orders/{orderId} settles the question. Never retry a submission before you have asked.

Deadlines

WhatHow longOn expiry
Prepared transaction5 minutesA later submission returns 410 CACHE_EXPIRED; prepare again
submitToken20 minutesNot the limiting factor

Sign and submit immediately after preparing. A delayed submission spends the five minute window while the price you quoted goes stale.

Cancelling

POST /orders/{contractId}/cancel, prepare measured at 11 to 23 seconds, then the same sign and submit steps. The body {"reason": "..."} is optional. A registered market maker sees cancelFee: { charged: false, amount: "0" }.

Use the current contractId from GET /orders. After a partial fill the previous one returns 404 CONTRACT_NOT_FOUND, because the remainder rests under a new one while keeping the same orderId.

Cancel one order per call; there is no bulk endpoint. Calls may be issued concurrently, subject to the capacity limit in Timings and limits.

Never withdraw from your wallet the funds backing a resting order. Doing so strands the order for good: neither your cancellation nor a Cardiv-side cancellation can complete, and clearing it takes manual work by Cardiv.

What happens to your funds

Exactly as in the app. A buy commits the quote token and a sell commits the base, locked in your own wallet from the moment the placement commits until the order fills or you cancel it. A fill moves both legs in one transaction, and a cancellation releases the lock in the same transaction as the cancellation.

Need help

Write to support@wolfedgelabs.com and include your party ID.

On this page

Need help

Write to support@wolfedgelabs.com and include your party ID.