# Compile a brief

> compile_audience: Compiles a plain English brief, such as 300 finance directors at law firms in Manchester, into an audience definition with a one-sentence readback, editable chips and any questions to answer first.

Source: https://emailmovers.com/mydatahub/docs/reference/mcp/compile_audience

Compiles a plain English brief, such as 300 finance directors at law firms in Manchester, into an audience definition with a one-sentence readback, editable chips and any questions to answer first. Use it first for a request in words, read the readback to the user and settle the questions before counting. Words that match no filter come back in unrecognised, never guessed. Free and needs no account; pass the audience to count_audience next. Lawful basis is UK GDPR Article 6(1)(f) legitimate interests; email audiences include corporate subscribers only by default (PECR), so sole traders and ordinary partnerships are left out unless the toggle is changed.

| Property | Value |
| --- | --- |
| Tool name | `compile_audience` |
| Position in tools/list | 7 of 22 |
| Cost | Free |
| Scope | None. Works without an account. |
| Annotations | readOnlyHint true, destructiveHint false, idempotentHint true, openWorldHint false |
| Kind | Read only; idempotent, not destructive, closed world |
| REST equivalent | [`POST /v1/audiences/compile`](https://emailmovers.com/mydatahub/docs/reference/rest/compile-audience.md) |

> **Not yet live.** MyDataHub v2 is built and tested locally and is not yet live. The v2 hosts open at launch, date to confirm. This is what `tools/list` returns from https://mydatahub.emailmovers.com/mcp once v2 launches.

## Input

The schema sets `additionalProperties` to false, so a member that is not listed is refused.

| Member | Type | Required | Description |
| --- | --- | --- | --- |
| `brief` | string | yes | A plain English brief, such as "300 finance directors at law firms in Manchester". |
| `dataset` | enum: `uk_contacts`, `ie_contacts`, `global_contacts` | no | The dataset an audience draws from. uk_contacts is live; ie_contacts and global_contacts are listed but not yet served. |

## Example call

The `params` of a `tools/call` request:

```json
{
  "name": "compile_audience",
  "arguments": {
    "brief": "300 finance directors at law firms in Manchester"
  }
}
```

## Output

The result carries `structuredContent` that matches this schema, and one line of text that leads with the number.

| Member | Type | Always present | Description |
| --- | --- | --- | --- |
| `audience` | `Audience` | yes | Who you want, as filters grouped by entity (company., site., contact., email., phone., signal.). The server fills its defaults (active companies, named emails, corporate subscribers, the current dataset_version) and returns the effective definition with every count. See [Audience](https://emailmovers.com/mydatahub/docs/audience.md). |
| `readback` | string | yes | The audience in one sentence, to confirm with the person. |
| `chips` | array of `Chip` | yes |  |
| `chips[].label` | string | yes | What the chip reads, such as Within 20 miles of Leeds. |
| `chips[].pointer` | string | yes | JSON pointer to the filter inside audience. |
| `chips[].from_brief` | string | yes | The words of the brief it came from. |
| `questions` | array of `BriefQuestion` | yes |  |
| `questions[].id` | string | yes |  |
| `questions[].text` | string | yes |  |
| `questions[].options` | array of object | yes |  |
| `unrecognised` | array of string | yes | Words of the brief that matched no filter, shown rather than guessed. |
| `quantity` | integer (0 or more) or null | yes | A quantity named in the brief, such as 300, for quote_order limit. |

## Errors

A failed call returns `isError` true. The text content leads with the sentence a person acts on, then the whole problem as JSON, with `code`, `detail`, `next_step` and `did_you_mean`. A 401 and a step-up 403 are answered at HTTP level so the client can start authorisation. See [Errors](https://emailmovers.com/mydatahub/docs/errors.md).
