One call runs the whole order for the quote’s lane: wallet checks, approvals, re-quoting when time is short, the pre-signing checks, the signature or transaction, the submission to the hub, and tracking until the order ends.

Options

Events

awaiting-wallet is the moment to tell the user to look at their wallet. On the wrap-native and swap-token lanes, submit-order runs while the deposit is still confirming: the order is registered as soon as the transaction is broadcast, and the SDK waits for the receipt afterwards.

The result

Tracking

The aggregator’s status (GET /order/{id}/status) is advisory. It can lag, or stop at executed, long after the order settled. The SDK therefore also reads the hub’s own chain facts (GET /onchain/{id}/fill) on every round:
  • a fill on chain emits filled: the recipient has been paid;
  • settled or refunded on chain ends the wait (decidedBy: "chain");
  • a terminal aggregator state (settled, finalized, failed, refunded) also ends it.
Fills usually show up seconds after submission. A wait gives up after 30 minutes with a timeout error, whose advice is to check the order’s status later; the order itself is unaffected. To follow an order outside executeQuote (after waitForCompletion: false, or from your history):
Open-flow orders are followed on the hub’s lifecycle view instead (GET /status/{id}): done when the recipient is paid (USER_PAID) or delivery is final, and a failure when the order goes to recovery (RECOVERY_ONLY). Tracking works the same with a project id (projectTransport): the chain facts and the lifecycle view are open to it.

Lost answers

A submission can succeed while its answer is lost (a timeout, a dropped connection, or the gateway’s EPX0050–EPX0053, among them EPX0052 when the hub took longer than the gateway’s 10 s). The gateway keeps a submission running at the hub when the caller disconnects, but not past its own 10 s. The hub records one submission per quote and answers a repeat with the original acknowledgement, so the SDK recovers without ever asking the user to sign again:
  1. it looks the order up by its derived hub order id, hex(sha256("infinity:v1:order:" + quoteId));
  2. if the hub has not seen it, it re-posts the same body once;
  3. if every answer is still lost, it throws OutcomeUnknownError with the hubOrderId to follow, and, on the transaction lanes, the transactionHash already on chain.
After an OutcomeUnknownError, never quote again or ask the user to sign again: the order may exist. Follow it with trackOrder(error.hubOrderId), or find it with client.findOrderByTx(sourceChain, error.transactionHash).

Executing on a server for your users

A call that names no user goes under hubTransport’s own subject (default unless you set another), so an order your backend executes for one of your users lands in that shared history like every other, and the hub does not know which user it was for. Two ways to keep your users apart (Authentication — your users):
  • Name the user. Get the quote with their subject, and pass the same subject to executeQuote, which sends it on the submission, a re-quote and the status reads. The hub then keeps that user’s quote, order and history apart:
    A client made for one user, createInteropClient({ transport, subject }), sends it on every call that reads it. The SDK checks the subject against the hub’s rule (^[A-Za-z0-9._@+~-]{1,128}$) before any call.
  • Record the user yourself, next to result.orderId and result.hubOrderId.
Calls your frontend makes through createInteropProxy are kept apart for you (Partner backend).