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

# Settlement Rules

> What changed for the Settlement Rules resource when migrating from HIFI API v2 to v3.

A Settlement Rule splits a Virtual Account's incoming deposits across multiple destinations by fee tier. The biggest change is the tier shape itself, plus how a rule's destination is specified. See the [platform-wide changes](/v3/guides/v2v3Migration/overview) for ID format, pagination, error shape, and idempotency.

## Endpoints

| v2 | v3 | Notes |
| - | - | - |
| `POST /v2/virtual-accounts/settlement-rules` | `POST /v3/virtual-accounts/settlement-rules` | Request body changed — see below. |
| `GET /v2/virtual-accounts/settlement-rules/:ruleId` | `GET /v3/virtual-accounts/settlement-rules/:settlementRuleId` | |
| `GET /v2/virtual-accounts/settlement-rules` | `GET /v3/virtual-accounts/settlement-rules` | List envelope changed to the standard `{data, pagination}` shape. Optional `chain` filter. |
| `POST /v2/.../settlement-rules/:ruleId/update` | `PATCH /v3/virtual-accounts/settlement-rules/:settlementRuleId` | Verb change. |
| `DELETE /v2/.../settlement-rules/:ruleId` | `DELETE /v3/virtual-accounts/settlement-rules/:settlementRuleId` | Same restriction: fails if the rule is currently applied to a Virtual Account. |
| `POST /v2/users/:userId/virtual-accounts/:accountId/settlement-rules/:ruleId` (apply) | `PUT /v3/virtual-accounts/:virtualAccountId/settlement-rules` (`settlementRuleId` in body) | Verb changed from `POST` with the rule ID in the path to `PUT` with the rule ID in the request body. |
| `DELETE /v2/users/:userId/virtual-accounts/:accountId/settlement-rules` (remove) | `DELETE /v3/virtual-accounts/:virtualAccountId/settlement-rules` | Same shape. |

## Request changes: tiers and destination

**v2** — tiers are `{min, max, value}` strings, with an empty string marking the open end of the first/last tier; destination is a raw wallet address:

```json theme={null}
{
  "chain": "POLYGON",
  "includeHIFIFee": true,
  "rules": [
    { "type": "PERCENTAGE", "calculationModel": "TIERED", "walletAddress": "0xabc123...",
      "tiers": [
        { "min": "", "max": "1000", "value": 1 },
        { "min": "1000", "max": "", "value": 0.5 }
      ]
    }
  ]
}
```

**v3** — tiers are `{upTo, value}` with a single ascending breakpoint (exactly one tier has `upTo: null` for the open-ended top tier); destination is a registered wallet reference:

```json theme={null}
{
  "requestId": "3f2504e0-4f89-11d3-9a0c-0305e82c3301",
  "chain": "POLYGON",
  "includeHIFIFee": true,
  "nickname": "Standard split",
  "rules": [
    { "type": "PERCENTAGE", "calculationModel": "TIERED", "walletId": "wlt_fkc0E4OsfHWZPNXiPhj4q",
      "tiers": [
        { "upTo": 1000, "value": 1 },
        { "upTo": null, "value": 0.5 }
      ]
    }
  ]
}
```

| v2 field | v3 field | Change |
| - | - | - |
| `tiers[].min` / `tiers[].max` | `tiers[].upTo` | **Changed shape** — `{min, max, value}` strings (`""` marks an open end) become `{upTo, value}`, a single ascending breakpoint per tier (`upTo: null` marks the open top tier) |
| `walletAddress` | `walletId` / `externalWalletId` | **Removed** as a raw address — exactly one registered wallet reference required instead |
| — | `requestId` | **New**, required |
| — | `nickname` | **New**, optional |

<Warning>
  <strong>Known gap, unchanged from v2:</strong> applying a rule to a Virtual Account doesn't verify the rule's `chain` matches the Virtual Account's destination chain, or block Solana. A mismatched apply can silently misroute a fee cut to the wrong chain. Verify the chain yourself before applying a rule.
</Warning>

## Response changes

**v2**

```json theme={null}
{
  "id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
  "chain": "POLYGON",
  "includeHIFIFee": true,
  "rules": [
    {
      "type": "PERCENTAGE",
      "calculationModel": "TIERED",
      "value": null,
      "walletAddress": "0xabc123...",
      "tiers": [
        { "min": "", "max": "1000", "value": 1 },
        { "min": "1000", "max": "", "value": 0.5 }
      ]
    }
  ]
}
```

**v3**

```json theme={null}
{
  "id": "sr_QW1e2r3t4y",
  "requestId": "3f2504e0-4f89-11d3-9a0c-0305e82c3301",
  "nickname": "Standard split",
  "chain": "POLYGON",
  "includeHIFIFee": true,
  "rules": [
    {
      "type": "PERCENTAGE",
      "calculationModel": "TIERED",
      "value": null,
      "walletId": "wlt_fkc0E4OsfHWZPNXiPhj4q",
      "externalWalletId": null,
      "tiers": [
        { "upTo": 1000, "value": 1 },
        { "upTo": null, "value": 0.5 }
      ]
    }
  ],
  "createdAt": "...",
  "updatedAt": "..."
}
```

| Change | Detail |
| - | - |
| `id` | Raw UUID → prefixed public ID (`sr_...`) |
| `walletAddress` | **Replaced** by resolved `walletId`/`externalWalletId` public IDs |
| `requestId` | **New** — now included in the response, not just accepted on create |
| `nickname` | **New** |
| `createdAt` / `updatedAt` | **New** timestamps |

## ID format

Raw UUID in v2 → `sr_...` prefixed public ID in v3.


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.