# Create label

URL: https://docs.hanzo.ai/docs/openapi/label/risklabel

> Records a batch of ground truth against the entities it judges.

`POST /v1/label`

> [Label →](https://docs.hanzo.ai/docs/openapi/label) · [All API references →](https://docs.hanzo.ai/docs/openapi) · [Get started →](https://docs.hanzo.ai/docs/guides)

|               |                                        |
| ------------- | -------------------------------------- |
| **Address**   | `https://api.hanzo.ai/v1/label`        |
| **Method**    | `POST`                                 |
| **Operation** | `riskLabel`                            |
| **Auth**      | `Authorization: Bearer $HANZO_API_KEY` |

Records a batch of ground truth against the entities it judges.

Each assertion carries TWO times — when the judged event happened, and when
the assertion became knowable — and both are required. The second is what
keeps a chargeback that landed in June out of a model that had to decide in
February.

It is idempotent on the CONTENT of an assertion, so a webhook that redelivers
is safe. It never overwrites: a source that corrects itself later files a NEW
assertion, which wins from the moment it became knowable and leaves every
earlier observation instant seeing exactly what it saw.

The asserter is stamped from the validated credential and is not a body field.

## Request

9 fields, body `application/json` (required).

| Field                  | In   | Type                   | Required | Description                                                                                                             |
| ---------------------- | ---- | ---------------------- | -------- | ----------------------------------------------------------------------------------------------------------------------- |
| `labels`               | body | label.riskLabelFact\[] | —        | Labels is the batch.                                                                                                    |
| `labels[].at`          | body | string                 | —        | At is when the judged event happened, RFC 3339.                                                                         |
| `labels[].confidence`  | body | number (double)        | —        | Confidence in \[0,1].                                                                                                   |
| `labels[].disposition` | body | string                 | —        | Disposition is productive, unproductive, or empty for an explicit unjudged — the AML engine's own vocabulary, verbatim. |
| `labels[].evidence`    | body | string                 | —        | Evidence points at the record this conclusion came from: a dispute id, a case id, a decision id.                        |
| `labels[].kind`        | body | string                 | —        | Kind is what the subject is: account, agent, merchant, payout, person, session or transaction.                          |
| `labels[].seen`        | body | string                 | —        | Seen is when this assertion became KNOWABLE, RFC 3339.                                                                  |
| `labels[].source`      | body | string                 | —        | Source is who asserted: chargeoff, dispute, case, refund, review or sample.                                             |
| `labels[].subject`     | body | string                 | —        | Subject identifies the thing being judged, in the tenant's own namespace.                                               |

## Response

| Status    | Body               | Meaning |
| --------- | ------------------ | ------- |
| `200`     | label.riskLabelOut | ok      |
| `default` | problem-details    | refused |

`200` body — 9 fields.

| Field               | In   | Type                     | Always | Description                                                                                                                                                 |
| ------------------- | ---- | ------------------------ | ------ | ----------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `duplicate`         | body | integer (int64)          | —      | Duplicate is how many members this tenant already held, byte for byte.                                                                                      |
| `mirror`            | body | string                   | —      | Mirror names why the columnar copy did not take this batch, when it did not.                                                                                |
| `pending`           | body | integer (int64)          | —      | Pending is how many assertions the derived copy is still to take.                                                                                           |
| `recorded`          | body | integer (int64)          | —      | Recorded is how many members became a NEW row in the tenant's record.                                                                                       |
| `refused`           | body | integer (int64)          | —      | Refused is how many members failed admission and were NOT recorded.                                                                                         |
| `results`           | body | label.riskLabelResult\[] | —      | Results is per fact, in the order sent, so a caller can retry exactly the members that were refused and can log the content digest of the ones that landed. |
| `results[].id`      | body | string                   | —      | ID is the content digest of the assertion — the id a redelivery of the same fact resolves to.                                                               |
| `results[].refusal` | body | string                   | —      | Refusal states what was wrong, for the refused.                                                                                                             |
| `results[].status`  | body | string                   | —      | Status is recorded, duplicate or refused.                                                                                                                   |

Failure carries the platform error shape — see [Errors](https://docs.hanzo.ai/docs/errors).

## Examples

**CLI**

```bash
hanzo label create
```

**SDK**

**.ts**

```ts
import { Configuration, LabelApi } from 'hanzoai';

const api = new LabelApi(new Configuration({ accessToken: process.env.HANZO_API_KEY }));
const { data } = await api.riskLabel({ labels: [{"at":"<at>","confidence":0,"disposition":"<disposition>","evidence":"<evidence>"}] });
```

**.py**

```python
from hanzoai.cloud import ApiClient, Configuration
from hanzoai.cloud.api import LabelApi

client = ApiClient(Configuration(access_token=os.environ["HANZO_API_KEY"]))
result = LabelApi(client).risk_label(labels=[{"at":"<at>","confidence":0,"disposition":"<disposition>","evidence":"<evidence>"}])
```

**.go**

```go
cfg := hanzoai.NewConfiguration()
cfg.AddDefaultHeader("Authorization", "Bearer "+os.Getenv("HANZO_API_KEY"))
client := hanzoai.NewAPIClient(cfg)

resp, _, err := client.LabelAPI.RiskLabel(context.Background()).Execute()
if err != nil {
	return err
}
```

**.rs**

```rust
use hanzo_client::apis::{configuration::Configuration, label_api};

let mut cfg = Configuration::new();
cfg.bearer_access_token = std::env::var("HANZO_API_KEY").ok();

let result = label_api::risk_label(&cfg, Default::default()).await?;
```

**.java**

```java
import ai.hanzo.cloud.ApiClient;
import ai.hanzo.cloud.api.LabelApi;

ApiClient client = new ApiClient();
client.setBearerToken(System.getenv("HANZO_API_KEY"));

var result = new LabelApi(client).riskLabel();
```

**HTTP**

```bash
curl -X POST https://api.hanzo.ai/v1/label \
  -H "Authorization: Bearer $HANZO_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
       "labels": [
         {
           "at": "<at>",
           "confidence": 0,
           "disposition": "<disposition>",
           "evidence": "<evidence>"
         }
       ]
     }'
```

**MCP**

Tool `label`, op `riskLabel` — POST the JSON-RPC envelope to `https://api.hanzo.ai/v1/mcp`.

```bash
curl -X POST https://api.hanzo.ai/v1/mcp \
  -H "Authorization: Bearer $HANZO_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
       "jsonrpc": "2.0",
       "id": 1,
       "method": "tools/call",
       "params": {
         "name": "label",
         "arguments": {
           "op": "riskLabel",
           "input": {
             "labels": [
               {
                 "at": "<at>",
                 "confidence": 0,
                 "disposition": "<disposition>",
                 "evidence": "<evidence>"
               }
             ]
           }
         }
       }
     }'
```

---

[Label API](https://docs.hanzo.ai/docs/openapi/label) · [All Hanzo APIs](https://docs.hanzo.ai/docs/openapi) · [Interactive reference](https://docs.hanzo.ai/docs/openapi/reference)
