> ## Documentation Index
> Fetch the complete documentation index at: https://v3.docs.derive.xyz/llms.txt
> Use this file to discover all available pages before exploring further.

# RFQ Trading

> Request a quote on a multi-leg package, collect maker quotes, and execute the block atomically.

The RFQ (request-for-quote) workflow lets a **taker** request a price on a package of one
or more instruments and execute it as a single atomic block trade against a **maker**'s
quote. It is the venue for large or multi-leg structures that would be hard to fill on the
public orderbook.

Every RFQ method is a `private/*` call and works over both WebSocket and HTTP POST. See
[Authentication](/authentication/session-login) for session login and [Endpoints](/getting-started/introduction#endpoints) for
endpoints.

<CardGroup cols={2}>
  <Card title="Taker" icon="user">
    Initiates the RFQ, collects incoming quotes, and signs the execution that fills the block.
  </Card>

  <Card title="Maker" icon="store">
    Discovers open RFQs, prices them, and submits signed quotes that the taker can execute.
  </Card>
</CardGroup>

## Legs and packages

An RFQ is defined by its **legs**. Each leg names an instrument, an amount, and a side:

<ParamField path="instrument_name" type="string" required>
  Instrument the leg trades (e.g. `ETH-PERP`).
</ParamField>

<ParamField path="amount" type="string" required>
  Contract quantity as a decimal string.
</ParamField>

<ParamField path="direction" type="string" required>
  `buy` or `sell` — the taker's side of this leg.
</ParamField>

A single-leg RFQ is a simple block; multi-leg RFQs let you price spreads, straddles, and
delta-hedged option structures as one package that fills all-or-nothing at a single
`total_cost`.

<Info>
  Instrument naming conventions are covered on the market-data reference. Resolve exact, currently-tradeable names with
  `public/get_all_live_instruments` before submitting an RFQ.
</Info>

## Signed actions and scopes

The RFQ **request itself is an unsigned intent** — it does not move funds. The state-changing
steps are **EIP-712 signed actions** under the RFQ module:

* The maker signs each **quote** (`private/send_quote`, `private/replace_quote`).
* The taker signs the **execution** (`private/execute_quote`).

These signatures carry a `signer`, `signature`, `nonce`, `signature_expiry_sec`, and `max_fee`,
and are re-verified by the protocol. See [Action signing](/authentication/action-signing) for the `Action`
struct, the RFQ module address, and the nonce/expiry conventions.

Each RFQ method requires the `trade:rfq:<asset>` protocol scope for **every** asset type its
legs touch (`trade:rfq:option`, `trade:rfq:perp`, `trade:rfq:spot`, or `trade:rfq:all`).
Cancel methods only require **any one** RFQ trade scope. See [Access scopes](/authentication/access-scopes).

| Method                                                        | Signed      | Scope requirement                 |
| ------------------------------------------------------------- | ----------- | --------------------------------- |
| `private/send_rfq`                                            | No          | `trade:rfq:<asset>` for every leg |
| `private/send_quote` / `private/replace_quote`                | Yes (maker) | `trade:rfq:<asset>` for every leg |
| `private/execute_quote`                                       | Yes (taker) | `trade:rfq:<asset>` for every leg |
| `private/cancel_rfq` / `private/cancel_quote` / batch cancels | No          | any one `trade:rfq:*`             |

## Taker flow

<Steps>
  <Step title="Submit the RFQ">
    Call `private/send_rfq` with the package legs. Leave `counterparties` empty to open the RFQ to all makers, or list
    wallet addresses to direct it privately.
  </Step>

  <Step title="Collect quotes">
    Poll `private/poll_quotes` for quotes received on your RFQs, or subscribe to the `{subaccount_id}.quotes` and `     {subaccount_id}.best.quotes` channels for live updates. Track your RFQ's own status on `{wallet}.rfqs`.
  </Step>

  <Step title="Pick the best quote">
    Call `private/rfq_get_best_quote` with your legs and direction to get the best executable quote for the package.
  </Step>

  <Step title="Execute">
    Sign and submit `private/execute_quote` with the chosen `quote_id`. The engine re-reads the RFQ and maker quote and
    settles the block atomically.
  </Step>
</Steps>

### Example: `private/send_rfq`

<CodeGroup>
  ```typescript TypeScript (SDK) theme={null}
  import { DeriveClient } from '@derivexyz/derive-ts';

  const client = new DeriveClient({
    network: 'mainnet',
    wallet: process.env.PRIVATE_KEY!,
  });
  await client.connect();
  await client.login(); // RFQ methods are all private

  // Unsigned intent: request quotes for a two-leg covered-call package.
  const rfq = await client.rfq.sendRfq({
    subaccountId: 1234,
    legs: [
      { instrumentName: 'ETH-PERP', amount: '10', direction: 'buy' },
      { instrumentName: 'ETH-20260925-3000-C', amount: '10', direction: 'sell' },
    ],
    label: 'eth-covered-call',
    maxTotalCost: '500',
    partialFillStep: '1',
  });

  console.log(
    `RFQ ${rfq.rfq_id} open until ${new Date(rfq.valid_until).toISOString()}`
  );
  ```

  ```python Python (SDK) theme={null}
  # Coming soon.
  ```

  ```rust Rust (SDK) theme={null}
  // Coming soon.
  ```

  ```bash cURL theme={null}
  # X-Derive* headers: session auth (see /authentication/session-login).
  # send_rfq is an unsigned intent, so the body carries no EIP-712 signature.
  curl -X POST https://api.derive.xyz/v3/private/send_rfq \
    -H "Content-Type: application/json" \
    -H "X-DeriveWallet: $WALLET_ADDRESS" \
    -H "X-DeriveTimestamp: $TS" \
    -H "X-DeriveSignature: $SIG" \
    -d '{
      "subaccount_id": 1234,
      "legs": [
        { "instrument_name": "ETH-PERP", "amount": "10", "direction": "buy" },
        { "instrument_name": "ETH-20260925-3000-C", "amount": "10", "direction": "sell" }
      ],
      "label": "eth-covered-call",
      "max_total_cost": "500",
      "min_total_cost": null,
      "partial_fill_step": "1",
      "counterparties": null
    }'
  ```

  ```json Request theme={null}
  {
    "id": "1",
    "jsonrpc": "2.0",
    "method": "private/send_rfq",
    "params": {
      "subaccount_id": 1234,
      "legs": [
        { "instrument_name": "ETH-PERP", "amount": "10", "direction": "buy" },
        {
          "instrument_name": "ETH-20260925-3000-C",
          "amount": "10",
          "direction": "sell"
        }
      ],
      "label": "eth-covered-call",
      "max_total_cost": "500",
      "min_total_cost": null,
      "partial_fill_step": "1",
      "counterparties": null
    }
  }
  ```

  ```json Response theme={null}
  {
    "id": "1",
    "jsonrpc": "2.0",
    "result": {
      "rfq_id": "f2b1c0de-1234-4a56-8b90-abcdef012345",
      "subaccount_id": 1234,
      "wallet": "0x1a2b...",
      "label": "eth-covered-call",
      "status": "open",
      "valid_until": 1758801000000,
      "legs": [
        { "instrument_name": "ETH-PERP", "amount": "10", "direction": "buy" },
        {
          "instrument_name": "ETH-20260925-3000-C",
          "amount": "10",
          "direction": "sell"
        }
      ],
      "max_total_cost": "500",
      "min_total_cost": null,
      "filled_pct": "0"
    }
  }
  ```
</CodeGroup>

<ResponseField name="rfq_id" type="string (uuid)">
  Identifier used to reference this RFQ in quotes, polls, and execution.
</ResponseField>

<ResponseField name="status" type="string">
  One of `open`, `filled`, `cancelled`, `expired`.
</ResponseField>

<ResponseField name="valid_until" type="integer">
  Millisecond timestamp after which the RFQ expires and no longer accepts quotes.
</ResponseField>

<Note>
  An RFQ is quotable only for a bounded window after creation (`valid_until`). The default window is 10 minutes.

  <Info>
    The exact window is deployment-specific and may differ per environment; confirm it for your target environment.
  </Info>
</Note>

Optional `send_rfq` params: `label`, `counterparties`, `min_total_cost`, `max_total_cost`
(decimal strings bounding the acceptable package cost), `partial_fill_step` (minimum fill
increment, default `1`), `client`, `extra_fee`, and `referral_code`.

## Maker flow

<Steps>
  <Step title="Discover RFQs">
    Poll `private/poll_rfqs` for RFQs visible to you (open-to-all, or those naming your wallet in `counterparties`), or
    subscribe to the `{wallet}.rfqs` channel.
  </Step>

  <Step title="Quote">
    Sign and submit `private/send_quote` with priced legs (each leg adds a `price` to the RFQ's `instrument_name` /
    `amount` / `direction`), a `direction`, and `max_fee`. Set `mmp` to opt the quote into [market-maker
    protection](/trading/market-maker-protection).
  </Step>

  <Step title="Update or pull">
    Use `private/replace_quote` to atomically cancel and re-submit a quote (provide one of `quote_id_to_cancel` or
    `nonce_to_cancel`), or `private/cancel_quote` / `private/cancel_batch_quotes` to withdraw quotes. Track your quotes
    on `{subaccount_id}.quotes`.
  </Step>
</Steps>

<Tip>
  Preview a quote or execution signature before sending with the public `public/send_quote_debug` and
  `public/execute_quote_debug` helpers — they return the EIP-712 encoded payload and hashes so you can byte-compare a
  rejected signature. They are a debugging aid, not a required step.
</Tip>

## Subscription channels

RFQ workflows are event-driven; prefer the WebSocket channels over repeated polling.

| Channel       | Address                       | Audience                          |
| ------------- | ----------------------------- | --------------------------------- |
| RFQ updates   | `{wallet}.rfqs`               | Maker discovery; taker RFQ status |
| Quote updates | `{subaccount_id}.quotes`      | Maker's own quotes                |
| Best quotes   | `{subaccount_id}.best.quotes` | Taker's best incoming quote       |

See [Subscriptions](/subscriptions) for the channel envelope and payload formats.

## Related methods

The full RFQ surface — including `private/get_rfqs`, `private/get_quotes`,
`private/cancel_rfq`, and `private/cancel_batch_rfqs` — is documented in the
**API Reference** tab.


## Related topics

- [Orderbook Trading](/trading/order-types.md)
- [Wallet rfqs](/api-reference/channels/walletrfqs.md)
- [Transfers & Withdrawals](/trading/transfers-withdrawals.md)
