---
title: "Per-state breakdown of a cross-state selection, before spending anything"
method: POST
path: "/api/v1/pipeline/trigger-multi/preview"
tags: ["pipeline", "pipeline"]
---

# Per-state breakdown of a cross-state selection, before spending anything

`POST /api/v1/pipeline/trigger-multi/preview`

## Request

- Base URL: `https://app.goodleads.club` (the document declares no server; this is the origin it was published from)
- URL: `https://app.goodleads.club/api/v1/pipeline/trigger-multi/preview`
- Auth: API key in header `X-API-Key`

Read-only. Resolve a cross-state selection into per-state counts and say
which states can actually start right now.

The confirm step for a fan-out that includes paid stages: vendor credits are
spent per record, so the operator approves the *shape* of the spend
(CO 41 · FL 28 · VA 9) rather than one lump total. Stamps no batches,
launches nothing — a preview must never be a way to trigger a run.

Scope only: which states a selection touches does not depend on what you
intend to run on them, so `stages` is rejected here as an unknown field.

## Request body

- MultiStateScopeRequest: The scope half of a fan-out: which records, across which states. Shared by the preview and the trigger so the states and counts an operator approves are resolved by exactly one piece of code. Deliberately carries NO stage list — which states a selection touches, and how many records it matches in each, does not depend on what you intend to run on them.
  - `states` string[], nullable: Restrict the fan-out to these states. Omit to run every state the selection touches. It narrows, never widens: a state named here that the selection does not touch is simply absent from the result.
  - `limit` integer, nullable: PER-STATE cap, not a total — `limit=100` across 5 states runs up to 500 records. One shared budget would have to pick which state gets starved; capping each leg is the predictable reading of 'take 100 from each'.
  - `entity_id` string, nullable: Comma/space/newline-separated UUIDs or GLIDs that may span states. Grouped by state, one run per state. Mutually exclusive with `filters`.
  - `filters` object[], nullable: Filter expression, same shape as POST /api/v1/leads/browse, WITHOUT a state clause — the fan-out supplies each leg's own. Mutually exclusive with `entity_id`.
  - `include_non_operating` boolean: Only meaningful with `filters`. Mirrors Browse's own default so the per-state counts match the number on the button the operator pressed — see `TriggerRequest.include_non_operating`.
  - `include_existing` boolean: Only meaningful with `filters`. See `TriggerRequest.include_existing`.
  - `include_registrations` boolean: Deprecated alias of include_existing (kept one release so saved requests resolve).

## Response `200`

Successful Response

- MultiStatePreviewResponse
  - `total_matched` integer, required
  - `total_will_run` integer, required
  - `states_ready` integer, required
  - `legs` MultiStatePreviewLeg[], required
    - `state` string, required
    - `matched` integer, required
    - `will_run` integer, required: `matched`, or the per-state `limit` if that is smaller.
    - `status` string, required
    - `detail` string, nullable
  - `capacity_note` string, nullable

## Other responses

- `422`: Validation Error

---

[API](https://skmtc.dev/goodleads/apis/formation-gtm-api.md) · [All operations](https://skmtc.dev/goodleads/apis/formation-gtm-api/llms.txt) · [OpenAPI document](https://skmtc.dev/goodleads/apis/formation-gtm-api/revisions/2068d13a82cf?raw)
