Classify

# REST API

Classify a form submission from any language with one HTTPS request. Send it from your server with the secret key of a Classify configuration.

## Request

**Method**

`POST`

**URL**

`https://api.botpoison.com/classify`

Shell

```bash
curl --request POST \
  --url 'https://api.botpoison.com/classify' \
  --header 'accept: application/json' \
  --header 'content-type: application/json' \
  --header 'authorization: Bearer sk_xxxxxxxx' \
  --data '{
    "content": {
      "name": "Jo",
      "email": "jo@example.com",
      "message": "Hello, could you send me a quote?"
    },
    "model": "spam-standard"
  }'
```

Send the key as an `Authorization: Bearer` header. Proxies and loggers already redact it. An `X-Api-Key` header works too, or `secretKey` in the body. If you send more than one, they must match, or the request fails with a 401.

### Body parameters

| Parameter | Type | Description |
| --- | --- | --- |
| content Required | string or object | What to classify: the text of a message box, or the whole form as an object of fields. See Content below. |
| model Required | string | The model to classify with, by name: spam-standard is the only model today. See Models. |
| secretKey Optional | string | The secret key of a Classify configuration. Required unless you send it in an Authorization or X-Api-Key header. |

### Content

Send a string for a single message box, or an object with one entry per form field. Send the whole form when you have it: the name, the email address and the other fields help the verdict as much as the message does.

JavaScript

```javascript
// A message box on its own: send the text
{ "content": "Hello, could you send me a quote?", "model": "spam-standard" }

// A whole form: send every field, as the form posted it
{
  "content": {
    "name": "Jo",
    "email": "jo@example.com",
    "company": "Example Ltd",
    "budget": 5000,
    "services": ["design", "hosting"],
    "message": "Hello, could you send me a quote?",
    "_redirect": "https://example.com/thanks"
  },
  "model": "spam-standard"
}
```

A field holds a string, a number, a boolean, null or a list of strings, numbers and booleans. A nested object is refused, so flatten it into fields of its own. Fields whose name starts with `_` are ignored, so form controls such as `_redirect` can stay in. Tracking fields such as `utm_source` and `gclid`, and the same parameters inside links, are ignored too. Empty fields are skipped, and a string is read as a single field named `message`.

A submission holds up to 100 fields and 20,000 characters, counted as one `name: value` line per field.

### Form-encoded body

Send `Content-Type: application/x-www-form-urlencoded` to post a form as it arrived, without building JSON. Every field is content, except two read as options: `secretKey` and `_model` for `model`. A field sent more than once is read as a list.

Shell

```bash
curl https://api.botpoison.com/classify \
  --header 'X-Api-Key: sk_xxxxxxxx' \
  --data-urlencode '_model=spam-standard' \
  --data-urlencode 'name=Jo' \
  --data-urlencode 'email=jo@example.com' \
  --data-urlencode 'message=Hello, could you send me a quote?'
```

## Response

JSON

```json
{
  "label": "clean",
  "score": 0.04,
  "model": "spam-standard"
}
```

`model` names the model that answered. See [Models](https://botpoison.com/documentation/classify/models/).

Branch on `label`: it is `spam` from a score of 0.8 and `clean` below it. `score` runs from 0 to 1 and is not a probability. Use it for a review queue or a form that needs its own line. See [Labels and scores](https://botpoison.com/documentation/classify/labels-and-scores/).

### Status codes

| Status | Meaning |
| --- | --- |
| 200 | A verdict. label is spam or clean, score runs from 0 to 1, and model names the model that answered. |
| 400 | `Malformed JSON body` `content must be a string or an object of fields` `content is empty` `content has more than 100 fields` `content is longer than 20,000 characters` `content field "x" must be a string, number, boolean or list of those` `Unknown model "x". Valid models: spam-standard`The body is not a JSON object, the content is missing, empty, too large or nested, or model names no model. |
| 401 | `Missing secret key` `Invalid secret key` `Secret key belongs to a Challenge configuration`The key is missing, unknown or rerolled, or is a Challenge key. A body key and a bearer token that differ are invalid. |
| 403 | `Classify is not enabled for this workspace`Classify has been turned off for the key's workspace. Contact us. |
| 413 | `Request body is too large`The body is larger than 1 MB. |
| 429 | `Too many requests for this key. Retry after a short wait.` `This workspace has used its Classify allowance for the last 30 days.`The key passed its rate limit (rate_limited), or a Free workspace is paused after its allowance (quota_exceeded). Wait the seconds Retry-After names. The call is not counted. |
| 500 | `Internal server error`The request failed on our side. Try again. |
| 503 | `Classification is temporarily unavailable`The model failed or took too long, and the call is not counted. Retry later with backoff. |

Every status other than 200 carries a `message` that says what is wrong.

JSON

```json
{
  "ok": false,
  "message": "Invalid secret key"
}
```

Paid plans are never cut off. If a workspace stays over for 3 months in a row, we'll get in touch about a plan that fits. On the Free plan, Classify keeps answering for 7 days after its allowance is reached, then pauses until the last 30 days drop back under it. See [Usage and limits](https://botpoison.com/documentation/platform/usage-and-limits/).
