> ## Documentation Index
> Fetch the complete documentation index at: https://developers.paxoslabs.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Order Submission

> Get quote calldata and submit cross-chain Transit orders.

This guide walks through the complete order submission flow: check authorization, fetch quote calldata, sign, and broadcast the transaction.

## Prerequisites

* A route identified from [Route Discovery](/v1.0.0/intro/products/transit/developers/guides/route-discovery)
* Wallet with sufficient offer asset balance (minimum \$35 USD equivalent)
* Native token (ETH) for gas and messaging fees

## Step 0: Check Authorization

Before submitting an order, check whether the offer token requires approval for the TransitStation contract.

`GET /v3/core/authorization`

| Parameter        | Type           | Required | Description                                                                  |
| ---------------- | -------------- | -------- | ---------------------------------------------------------------------------- |
| `spenderAddress` | hex string     | Yes      | TransitStation contract (get from quote `transaction.to` or route discovery) |
| `tokenAddress`   | hex string     | Yes      | Offer token address                                                          |
| `amount`         | decimal string | Yes      | Offer amount in base units                                                   |
| `userAddress`    | hex string     | Yes      | User's wallet address                                                        |
| `chainId`        | integer        | Yes      | Source chain ID                                                              |

### Response Variants

**`permit`** — Token supports EIP-2612. Sign off-chain, then pass to quote endpoint.

```json theme={null}
{
  "method": "permit",
  "permitData": {
    "domain": { "name": "USD Coin", "version": "2", "chainId": 1, "verifyingContract": "0xA0b8..." },
    "types": { "Permit": [...] },
    "value": { "owner": "0x...", "spender": "0x...", "value": "50000000", "nonce": "0", "deadline": "..." },
    "deadline": "..."
  }
}
```

**`approval`** — Standard ERC-20 approval required first.

```json theme={null}
{
  "method": "approval",
  "approvalTransaction": { "encoded": "0x095ea7b3..." }
}
```

**`already_approved`** — Sufficient allowance exists. Proceed to quote.

```json theme={null}
{ "method": "already_approved" }
```

### Handling Each Path

| Method             | Action                                                                                         |
| ------------------ | ---------------------------------------------------------------------------------------------- |
| `permit`           | Sign `permitData` via `eth_signTypedData_v4`, pass signature + deadline to quote               |
| `approval`         | Send approval tx (`to = tokenAddress`, `data = approvalTransaction.encoded`), wait for receipt |
| `already_approved` | Skip to Step 1                                                                                 |

## Step 1: Get Order Quote

`GET /v1/transit/orders/quote`

This endpoint returns everything needed to submit the transaction: the contract address, ABI-encoded calldata, and the native token value for messaging fees.

### Parameters

| Parameter               | Type           | Required    | Description                                                           |
| ----------------------- | -------------- | ----------- | --------------------------------------------------------------------- |
| `userAddress`           | hex string     | Yes         | Wallet receiving funds on destination chain                           |
| `offerAmount`           | decimal string | Yes         | Amount in offer-asset base units (min \$35 USD)                       |
| `offerAsset`            | hex string     | Yes         | Token address on source chain                                         |
| `wantAsset`             | hex string     | Yes         | Token address on destination chain                                    |
| `sourceChainId`         | integer        | Yes         | Source chain EVM ID                                                   |
| `destinationChainId`    | integer        | Yes         | Destination chain EVM ID                                              |
| `permitSignature`       | hex string     | Conditional | EIP-2612 permit signature (required with `permitDeadline`)            |
| `permitDeadline`        | integer        | Conditional | Permit expiry timestamp (required with `permitSignature`)             |
| `integratorFee`         | decimal string | Conditional | Fee in offer-asset base units (required with `integratorFeeReceiver`) |
| `integratorFeeReceiver` | hex string     | Conditional | Address receiving integrator fee                                      |
| `distributorCode`       | hex string     | No          | 32-byte tracking code (defaults to organization's configured value)   |
| `responseFormat`        | enum           | No          | `encoded` (default), `full`, or `structured`                          |

### Example Request

```bash theme={null}
curl "https://api.paxoslabs.com/v1/transit/orders/quote?\
userAddress=0x1234567890abcdef1234567890abcdef12345678&\
offerAmount=50000000&\
offerAsset=0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48&\
wantAsset=0x833589fcd6edb6e08f4c7c32d4f71b54bda02913&\
sourceChainId=1&\
destinationChainId=4663"
```

### Response

```json theme={null}
{
  "transaction": {
    "to": "0x...",
    "data": "0x...",
    "value": "1500000000000000"
  },
  "amountOut": "49990000",
  "protocolFee": "10000",
  "integratorFee": "0",
  "totalFees": "10000",
  "estimatedLatencyMs": 300000
}
```

## Step 2: Understand the Response

| Field                | Description                                            |
| -------------------- | ------------------------------------------------------ |
| `transaction.to`     | TransitStation contract address                        |
| `transaction.data`   | ABI-encoded `submitOrder` calldata                     |
| `transaction.value`  | Native token for messaging fee (wei)                   |
| `amountOut`          | Net amount credited after fees (want-asset base units) |
| `protocolFee`        | Protocol fee (offer-asset base units)                  |
| `integratorFee`      | Integrator fee if specified (offer-asset base units)   |
| `totalFees`          | Sum of protocol and integrator fees                    |
| `estimatedLatencyMs` | Expected delivery time in milliseconds                 |

## Step 3: Submit the Transaction

Broadcast the transaction using the returned `to`, `data`, and `value` fields.

### Code Example (viem)

```ts theme={null}
import { createWalletClient, createPublicClient, http } from 'viem'
import { mainnet } from 'viem/chains'
import { privateKeyToAccount } from 'viem/accounts'

const account = privateKeyToAccount('0x...')
const walletClient = createWalletClient({
  account,
  chain: mainnet,
  transport: http(),
})
const publicClient = createPublicClient({
  chain: mainnet,
  transport: http(),
})

const OFFER_ASSET = '0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48'
const OFFER_AMOUNT = '50000000'
const TRANSIT_STATION = '0x...' // from route discovery or prior quote

// Step 0: Check authorization
const authUrl = new URL('https://api.paxoslabs.com/v3/core/authorization')
authUrl.searchParams.set('spenderAddress', TRANSIT_STATION)
authUrl.searchParams.set('tokenAddress', OFFER_ASSET)
authUrl.searchParams.set('amount', OFFER_AMOUNT)
authUrl.searchParams.set('userAddress', account.address)
authUrl.searchParams.set('chainId', '1')

const auth = await fetch(authUrl).then((r) => r.json())

// Step 1: Build quote params
const quoteUrl = new URL('https://api.paxoslabs.com/v1/transit/orders/quote')
quoteUrl.searchParams.set('userAddress', account.address)
quoteUrl.searchParams.set('offerAmount', OFFER_AMOUNT)
quoteUrl.searchParams.set('offerAsset', OFFER_ASSET)
quoteUrl.searchParams.set('wantAsset', '0x...')
quoteUrl.searchParams.set('sourceChainId', '1')
quoteUrl.searchParams.set('destinationChainId', '4663')

// Handle authorization path
if (auth.method === 'permit') {
  const sig = await walletClient.signTypedData({
    account,
    domain: auth.permitData.domain,
    types: auth.permitData.types,
    primaryType: 'Permit',
    message: auth.permitData.value,
  })
  quoteUrl.searchParams.set('permitSignature', sig)
  quoteUrl.searchParams.set('permitDeadline', auth.permitData.deadline)
} else if (auth.method === 'approval') {
  const hash = await walletClient.sendTransaction({
    to: OFFER_ASSET as `0x${string}`,
    data: auth.approvalTransaction.encoded as `0x${string}`,
    chain: mainnet,
    account,
  })
  await publicClient.waitForTransactionReceipt({ hash })
}

// Fetch quote and submit
const { transaction } = await fetch(quoteUrl).then((r) => r.json())

const hash = await walletClient.sendTransaction({
  to: transaction.to as `0x${string}`,
  data: transaction.data as `0x${string}`,
  value: BigInt(transaction.value),
})

console.log('Transaction hash:', hash)
```

## Step 4: Record the Order ID

The transaction receipt contains an `OrderSubmitted` event with the order ID (a hex hash). Use this ID to track fulfillment via the [Order Tracking](/v1.0.0/intro/products/transit/developers/guides/order-tracking) endpoints.

## Response Formats

Control the transaction response structure with `responseFormat`:

| Format              | `data` | `abi` / `functionName` / `args` | Use Case                                         |
| ------------------- | ------ | ------------------------------- | ------------------------------------------------ |
| `encoded` (default) | Yes    | No                              | Direct signing with HSM or `eth_sendTransaction` |
| `full`              | Yes    | Yes                             | Debugging — see both encoded and decoded         |
| `structured`        | No     | Yes                             | Encode locally with your own tooling             |

## Distributor Codes

The optional `distributorCode` parameter accepts a 32-byte hex string (0x + 64 chars) for tracking order sources on-chain. If omitted, the quote uses your organization's configured default distributor code.

## Common Errors

| Error                          | Cause                                   | Fix                                 |
| ------------------------------ | --------------------------------------- | ----------------------------------- |
| `400` — Amount below minimum   | Offer amount \< \$35 USD                | Increase offer amount               |
| `400` — Invalid permit         | Missing `permitDeadline` with signature | Provide both or neither             |
| `400` — Invalid integrator fee | Missing `integratorFeeReceiver`         | Provide both or neither             |
| `404` — Route not found        | No route for asset pair                 | Check available routes              |
| On-chain revert                | Insufficient ETH for `value`            | Ensure balance covers messaging fee |
| On-chain revert                | Insufficient allowance                  | Run authorization check first       |

## Next Steps

<Card title="Order Tracking" icon="clock" href="/v1.0.0/intro/products/transit/developers/guides/order-tracking">
  Monitor order status and view execution history.
</Card>
