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

# Discover new options

> Find out what a choice judgment's escape option holds, get a proposal for the options it is missing, and review it before you create the version.

A choice judgment answers with one of its options, or with `none_of_the_above` when none of them fits. That escape option is where a new kind of complaint, a new abuse pattern or a new product question shows up first. Discovery reads what landed there and proposes the options your judgment is missing. It never changes the judgment: you review the proposal, edit it, and create the new version yourself.

Discovery is for choice judgments with fixed options. A `bool` or `score` judgment has no escape option; watch its [calibration report](/guides/measure-improve-tune) instead. A choice that [chooses among candidates](/guides/entity-matching) has one, but it means "no candidate matches", not a missing option, so discovery does not apply to it either.

## Know when to look: the escape alert

`escape_alert` is a setting of a choice judgment: the share of its answers over the last 7 days that were `none_of_the_above`, above which you want to know. It is off until you set it, and changing it creates no version.

<CodeGroup>
  ```ts TypeScript theme={"theme":{"light":"css-variables","dark":"css-variables"}}
  await ns.judgments.update("complaint_type", { escape_alert: 0.1 });
  ```

  ```python Python theme={"theme":{"light":"css-variables","dark":"css-variables"}}
  ns.judgments.update("complaint_type", escape_alert=0.1)
  ```
</CodeGroup>

When the share rises above it, three things happen, and nothing else:

* **The judgment gets a warning.** `GET` on the judgment lists `taxonomy_drift` in `warnings`, with the share and when it rose. The dashboard shows it on the judgment's page. It clears when the share falls back.
* **One event.** The [events feed](/guides/events-feed), and every [webhook endpoint](/guides/webhooks) that asks for it, gets one `judgment.taxonomy_drift` per rise, not one per answer. Staying above sends nothing more.
* **Nothing changes on its own.** Your answers, options and bill stay as they are. You run discovery when you want to.

```json theme={"theme":{"light":"css-variables","dark":"css-variables"}}
{
  "code": "taxonomy_drift",
  "message": "12% of the last 7 days' answers were none_of_the_above, above the alert at 10%: run discover to see what they have in common",
  "escape_share": 0.12,
  "since": "2026-09-29T06:00:00Z"
}
```

The share needs at least 20 answers in the 7 days before it can raise the warning, so a quiet judgment's first escape isn't a drift. The alert takes a number above 0 and at most 1; `null` turns it off. A namespace that inherits the judgment from a [template](/guides/templates) follows the template's alert, and gets its own warning and event from its own answers.

## Turn on suggestions

Discovery sends a sample of your documents to a third-party LLM provider, the same one that [suggests parts](/guides/composite-judgments#suggested-parts). That provider is one of the [subprocessors](/behavior#where-your-data-goes) listed in the data processing agreement. So it is **off by default**: an org admin turns on **Suggestions** in the organization's settings in the dashboard. Until then, `discover` is refused with `forbidden`.

## Run discovery

`POST /namespaces/{ns}/judgments/{name}/discover` with how far back to look (`window`, 7 days by default) and the most new options you want (`count`, 1 to 10, 5 by default):

```json theme={"theme":{"light":"css-variables","dark":"css-variables"}}
{"window": "7d", "count": 5}
```

<CodeGroup>
  ```ts TypeScript theme={"theme":{"light":"css-variables","dark":"css-variables"}}
  let job = await ns.judgments.discover("complaint_type", { window: "7d", count: 5 });
  while (job.status === "running") {
    await new Promise((resolve) => setTimeout(resolve, 5_000));
    job = await db.jobs.get(job.id);
  }
  console.log(job.proposal);
  ```

  ```python Python theme={"theme":{"light":"css-variables","dark":"css-variables"}}
  import time

  job = ns.judgments.discover("complaint_type", window="7d", count=5)
  while job["status"] == "running":
      time.sleep(5)
      job = db.jobs.get(job["id"])
  print(job["proposal"])
  ```
</CodeGroup>

It answers `202` with a `discover` job, which:

1. **Samples the escape.** It takes a sample of the documents whose answer in the window is `none_of_the_above`, or whose `escape_p` is at or above the judgment's threshold on `none_of_the_above` if you set one.
2. **Asks for options.** It sends the sample, compiled with the judgment's context recipe exactly as it is judged, to a third-party LLM provider with your question and your current options. The provider proposes up to `count` new options, each with a description and the sampled documents it covers.
3. **Checks them.** It checks the proposed options against the sample in shadow, beside the current ones, as a [shadow report](/guides/measure-improve-tune) checks a new version. This is free and changes no answer.

Discovery is free, and limited to 10 calls per organization a day, across all its namespaces and judgments. These are its own: discovery takes none of [suggested parts](/guides/composite-judgments)' daily calls, and they take none of its. Past them it is `rate_limited`, with `details.limit` (10) and when the allowance renews in `details.resets_at`, the next midnight UTC. The call is taken when the job starts, and a busy model is waited out rather than failing the job. A job that fails before the model has run for it gives the call back.

## Read the proposal

When the job is `done`, its `proposal` is a new version's options, the current ones first:

```json theme={"theme":{"light":"css-variables","dark":"css-variables"}}
{
  "options": [
    {"value": "billing", "description": "Charges, invoices, refunds."},
    {"value": "delivery", "description": "Late, lost or damaged parcels."},
    {"value": "account_access", "description": "Locked out, password resets and two-factor codes that never arrive."},
    {"value": "subscription_cancel", "description": "Trying to cancel a subscription and being unable to."}
  ],
  "proposed": [
    {"value": "account_access", "description": "Locked out, password resets and two-factor codes that never arrive.", "absorbs": 71, "sample_ids": ["t_90412", "t_90388", "t_90377"]},
    {"value": "subscription_cancel", "description": "Trying to cancel a subscription and being unable to.", "absorbs": 44, "sample_ids": ["t_90401", "t_90356"]}
  ],
  "sampled": 200,
  "escape_documents": 1318,
  "unlabelled": 85
}
```

* **`escape_documents`** is how many documents in the window escaped; **`sampled`** is how many of them the job read.
* **`absorbs`** is how many sampled documents the proposed version answered with that option; **`sample_ids`** are the ones the LLM said the option covers. Open a few of them to see what the option really means.
* **`unlabelled`** is how many sampled documents the proposed version still answered `none_of_the_above`. A large number means the escape holds more than one new thing, or things no option should cover.

The provider may propose fewer options than `count`, or none when the escaped documents share nothing new. That job is still `done`: `proposed` is empty, `options` are your current ones, and `unlabelled` counts the sampled documents that escaped.

### When a job fails

A job fails, with `proposal` null, only when it got no options to check. Its `error` says why:

| `error` | What to do |
| - | - |
| `the model stayed busy through every retry; run discover again later` | The provider was busy for a few minutes. Run discover again later. |
| `the model did not reply with options; run discover again` | The reply was not a list of options. Run discover again; each run takes a call for the day. |
| `discovery failed because of a fault on our side; run discover again later` | Ours to fix. The call is given back. |

## Review before you create the version

The proposal is a draft. The review is where most of its value is, so don't accept it unedited:

* **Some proposals are a narrower case of an option you have.** Added as they are, they take documents from their parent option. Fold a proposal like that into the parent option's description instead of adding it, or delete it.
* **A new option next to an old one won't take all of its documents.** The neighbour keeps some of them. Sharpen both descriptions so the line between them is clear, and read the shadow report when you activate.
* **A small new kind may not come back as its own option.** When it is a small part of what escaped, look for it in `unlabelled` and in the sampled documents.

Then create the version with the options you settled on, as you create any version. Activating it runs the ordinary [shadow report](/guides/measure-improve-tune) over up to 1,000 of your documents, which shows what would change before anything does. In the dashboard, the judgment's **Discover** tab shows the proposal as an editable list of options, with the change to the definition beside it, and creates the version from what you edited.

## Limits

| | |
| - | - |
| `count` | 1 to 10 new options, 5 by default |
| Sample | a sample of recent escaped documents |
| Calls | 10 per organization a day, apart from suggested parts' |
| `escape_alert` | above 0 and at most 1, or `null` (off); 7 days of answers, at least 20 |
| Judgments | choice judgments with fixed options; `bool`, `score` and a choice among a relation's candidates are refused with `invalid_request` |


## Related topics

- [Judgments](/concepts/judgments.md)
- [Propose options for what the escape option holds](/api-reference/judgments/propose-options-for-what-the-escape-option-holds.md)
- [Create a judgment, or a new version of an existing name](/api-reference/judgments/create-a-judgment-or-a-new-version-of-an-existing-name.md)
- [Limits](/limits.md)
- [Measure, improve, tune](/guides/measure-improve-tune.md)


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