URL: /code/apps/crm/advance · Id: `page:/code/apps/crm/advance`

# Deal.advance

> Moves a deal to its next stage once every field that stage requires is filled.

POST https://api.sb/&#123;your-domain&#125;/deals/&#123;deal&#125;/advance

Moves a [deal](https://startupbuilder.dev/business/nouns/deal) to its next stage once every field that stage requires is filled.

- **Action class:** None
- **Approval:** Runs on its own
- **Emits:** `Deal.advanced`
- **Venues:** [1 Venues](#on-each-venue)
- **Price:** Free

```text title="Run it · Ask"
Move the Harborview deal to proposed now that the quote is attached.
```

```ts title="Run it · SDK"
import { $ } from 'startup-builder'

const result = await $.try.Deal.advance({ deal: 'https://api.sb/leaseline.app/deals/deal_Hv8kD2nQ4s', stage: 'proposed' })
```

```json title="Run it · Response"
{
  "api": "https://api.sb/leaseline.app",
  "deal": {
    "$id": "https://api.sb/leaseline.app/deals/deal_Hv8kD2nQ4s",
    "$type": "Deal",
    "status": "proposed",
    "value": {
      "amount": 1788,
      "currency": "USD"
    }
  },
  "action": {
    "operation": "Deal.advance",
    "mode": "try",
    "status": "done"
  }
}
```

Its Inputs, Outputs, Effects and guards quote [the hub’s `Deal.advance`](https://startupbuilder.dev/business/nouns/deal/advance); this page adds what each Venue honors, its limits and a worked call. It is one of the [Verbs](https://startupbuilder.dev/business/nouns/verb) of [CRM](/code/apps/crm#verbs).

## Inputs
| Name | Type | Meaning |
| --- | --- | --- |
| `deal` | `Deal` | Required. The deal. |
| `stage` | `string` | The target stage; omitted, the next one. Optional. |

## Outputs
| Field | Type | What `null` means |
| --- | --- | --- |
| `deal` | `Deal` | Never null: the deal in its new stage. |

## Effects
**Action class**

None: no approval rule names it, so it runs within its seat’s Permissions and Limits

**Modes**

- `try`: Runs every check and returns the record as it would be; nothing is stored.
- `send`: Returns a pending Action at once; `Deal.advanced` fires when it is done.
- `do`: Waits for the Action to finish and returns the record.

**Idempotency**

Only with a key: the same `Idempotency-Key` and input return the first Action, and the same key with other input returns `409`.

**Saved or shared**

The deal is saved as the call leaves it, with the Action that changed it.

**Emits**

`Deal.advanced` with `{ deal }`

**Performed by**

[Sales lead](https://startupbuilder.dev/agents/sales/sales-lead)

**Price**

Free on your own account: the platform charges nothing for the call.

## On each Venue
| Venue | Formats |
| --- | --- |
| [The CRM you already use](/code/integrations/your-crm#limits) | None. |

Each Venue’s caps, review and rate limits are on its integration page, linked from its row. A field marked Not sent is one that Venue has no place for; the call never fails on it.

## What try does
| Account | What try does |
| --- | --- |
| [The CRM you already use](/code/integrations/your-crm#try) | Reads your CRM and returns what one sync would change on each side, record by record; nothing is written to either. |

## Refuses when
| Guard | Refuses | Error |
| --- | --- | --- |
| `stage-fields` | Refuses when a field the target stage requires is empty, and names each one. | `refused` |

Through a connected account it can also meet [the shared account refusals](/code/refusals#accounts).

## When it waits
Returns in one response; nothing waits.

## Example
In `send` mode the call returns its pending Action at once, and `Deal.advanced` delivers the result.

**Ask**

```text
Move the Harborview deal to proposed now that the quote is attached.
```

**API**

```bash
curl -X POST "https://api.sb/leaseline.app/deals/deal_Hv8kD2nQ4s/advance?mode=send" \
  -H "Authorization: Bearer $SB_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{
  "stage": "proposed"
}'
```

**CLI**

```bash
npx startup-builder do Deal.advance --send --data '{
  "stage": "proposed"
}'
```

`--send` returns the pending Action at once.

**MCP**

```json
{
  "name": "do",
  "arguments": {
    "mode": "send",
    "code": "return await $.Deal.advance({ stage: 'proposed' })"
  }
}
```

**SDK**

```ts
import { $ } from 'startup-builder'

const result = await $.send.Deal.advance({
  deal: 'https://api.sb/leaseline.app/deals/deal_Hv8kD2nQ4s',
  stage: 'proposed',
})
```


```json title="Response, in send mode"
{
  "mode": "send",
  "action": {
    "$id": "https://api.sb/leaseline.app/actions/action_Sd3kQ9vT2w",
    "operation": "Deal.advance",
    "status": "pending",
    "reason": "running"
  }
}
```

To retry, send the same `Idempotency-Key`: the retry returns the first answer for $0. A new key reads again.

## Used by
- **Services:** [Sales closing](/capabilities/convert-visitors/sales-closing)
- **Integrations:** [The CRM you already use](/code/integrations/your-crm)

## Related
[`Lead.qualify`](/code/apps/crm/qualify) · [`Lead.assign`](/code/apps/crm/assign-lead) · [`Deal.win`](/code/apps/crm/win) · [`Deal.lose`](/code/apps/crm/lose) · [`Lead.nurture`](/code/apps/crm/nurture) · [`Lead.convert`](/code/apps/crm/convert) · [`Lead.disqualify`](/code/apps/crm/disqualify) · [`Deal.assign`](/code/apps/crm/assign-deal) · [`Deal.propose`](/code/apps/crm/propose) · [`Contact.merge`](/code/apps/crm/merge-contact) · [`Organization.merge`](/code/apps/crm/merge-organization)