# Develop or amend an idea

> Compile a plain-words idea into a rule, or amend an existing one by id. Free, but needs a positive balance. Any chat on an idea sends it back to the start of the conveyor.

Source: https://firmtape.com/docs/developers/lab/chat

Compile a plain-words idea into a rule, or amend an existing one by `id`. Free, but needs a positive balance. Any chat on an idea sends it back to the start of the conveyor.

`POST /api/lab/chat`

Plan LAB · Key scope lab · Limit Credits; one idea on the conveyor at a time · Version 1.0.0 · Since 2026-08-12

**This endpoint serves:** [LAB: LAB from a script](https://firmtape.com/docs/lab#lab-api), [LAB: The LAB desk and the backtest](https://firmtape.com/docs/lab#backtester). **Plan:** [LAB](https://firmtape.com/features/lab). LAB credits: developing an idea is free, a backtest or an optimize pass is one credit, the desk is free once an idea is tested. LIVE includes 5 credits a month.

## Body

| Field | Meaning | Unit |
| --- | --- | --- |
| `message` (string) | Plain-English research idea |  |
| `id` (string) | Existing LAB idea id to amend |  |

## Response

`kind: "spec"` with the compiled idea, or `kind: "chat"` with a question.

| Field | Meaning | Unit |
| --- | --- | --- |
| `kind` (spec \| chat \| error) | `spec`, `chat` or `error`. |  |
| `say` (string) | LAB's answer in words. |  |
| `idea` (object) | With `spec`: `{ id, name, spec }`. |  |
| `errors` (array) | With `error`: what could not compile. |  |

## Errors

| Status | Code | What to do |
| --- | --- | --- |
| 400 |  | A parameter is wrong. |
| 401 |  | No key, or an unknown or revoked one. Send a `lab` key. |
| 402 |  | No credits. Buy credits on the LAB page. |
| 404 |  | No such idea or job. Check the id. |
| 422 |  | The rule could not be compiled or was refused (refunded). Change the rule. |

## Request

```sh
curl -X POST \
  -H "Authorization: Bearer $FIRMTAPE_LAB_KEY" \
  "https://firmtape.com/api/lab/chat"
```

```python
import os, requests

H = {"Authorization": f"Bearer {os.environ['FIRMTAPE_LAB_KEY']}"}
r = requests.post("https://firmtape.com/api/lab/chat", headers=H)
print(r.status_code, r.text[:500])
```

```js
const r = await fetch("https://firmtape.com/api/lab/chat", {
  method: "POST",
  headers: { Authorization: `Bearer ${process.env.FIRMTAPE_LAB_KEY}` },
});
console.log(r.status, await r.text());
```

## Example response

```json
{
  "kind": "spec",
  "say": "Compiled: fade a +3 sigma stretch above vwap.",
  "idea": {
    "id": "i_abc123def456",
    "name": "vwap stretch fade",
    "spec": {}
  }
}
```

## Changes

- 2026-08-12: Added.
