LanaChat

API: AI Brains, drafts and the Playground

6 min readUpdated Markdown

An AI Brain holds how the AI sells for a creator: its sales phases, rules and settings. You change a draft, test it in the Playground, then publish it; the live brain only changes on publish. A brain is linked to one creator and can be reused by her accounts.

Endpoints #

MethodPathDescriptionPermissionStatus
GET/brainsList brains (creator_id=)can_enginePlanned
POST/brainsCreate a brain for a creator, empty or copied from another (copy_from)can_enginePlanned
GET/brains/{id}The live version of a braincan_enginePlanned
PATCH/brains/{id}Rename it or link it to another creatorcan_enginePlanned
DELETE/brains/{id}Delete a brain no account usescan_enginePlanned
GET/brains/{id}/draftThe current draft and what differs from livecan_enginePlanned
PATCH/brains/{id}/draftChange the draft (phases, rules, settings)can_enginePlanned
DELETE/brains/{id}/draftThrow the draft awaycan_enginePlanned
POST/brains/{id}/publishPublish the draft; it becomes live on every linked accountcan_publishPlanned
GET/brains/{id}/versionsPublished versions, newest firstcan_enginePlanned
POST/brains/{id}/versions/{version}/restoreCopy an old version into the draftcan_enginePlanned
POST/playground/{brain_id}/messageSend a test message to the draft and get the AI's replycan_enginePlanned
DELETE/playground/{brain_id}/sessionStart the test conversation overcan_enginePlanned

The brain object #

{
  "id": "br_lea_main",
  "name": "Lea · main",
  "creator_id": "cr_lea",
  "version": 12,
  "published_at": "2026-10-04T21:10:00Z",
  "has_draft": true,
  "accounts": ["acc_1001", "acc_1004"],
  "phases": [
    { "key": "warm_up", "name": "Warm up", "enabled": true },
    { "key": "first_offer", "name": "First offer", "enabled": true }
  ]
}
FieldTypeDescription
idstringStarts with br_
namestringIts name in the Console
creator_idstringThe creator it is linked to
versionnumberThe live version; it goes up by one on each publish
published_atstring or nullWhen the live version was published, ISO 8601 UTC
has_draftbooleantrue when a draft differs from the live version
accountsarray of stringsTelegram accounts that answer with this brain
phasesarraySales phases: key, name and whether each one is enabled

Brains #

List brains #

GET /brains · can_engine

ParameterTypeRequiredDescription
creator_idstringNoOnly this creator's brains
limit, cursornumber, stringNoPagination
curl "https://api.lanachat.ai/v1/brains?creator_id=cr_lea" \
  -H "Authorization: Bearer $LANACHAT_TOKEN"
{
  "data": [
    { "id": "br_lea_main", "name": "Lea · main", "creator_id": "cr_lea", "version": 12, "published_at": "2026-10-04T21:10:00Z", "has_draft": true, "accounts": ["acc_1001", "acc_1004"], "phases": [ { "key": "warm_up", "name": "Warm up", "enabled": true }, { "key": "first_offer", "name": "First offer", "enabled": true } ] }
  ],
  "next_cursor": null
}

Create a brain #

POST /brains · can_engine

ParameterTypeRequiredDescription
creator_idstringYesThe creator it is for
namestringNoIts name in the Console
copy_fromstringNoId of a brain to copy; without it the brain starts empty
curl -X POST https://api.lanachat.ai/v1/brains \
  -H "Authorization: Bearer $LANACHAT_TOKEN" \
  -H "Idempotency-Key: $(uuidgen)" \
  -H "Content-Type: application/json" \
  -d '{"creator_id": "cr_lea", "name": "Lea · TikTok test", "copy_from": "br_lea_main"}'

The answer is the new brain (201). A copy_from brain that does not exist in this workspace answers 404.

Get a brain #

GET /brains/{id} · can_engine

curl https://api.lanachat.ai/v1/brains/br_lea_main \
  -H "Authorization: Bearer $LANACHAT_TOKEN"

The answer is the live version, as the brain object. The draft is read with GET /brains/{id}/draft.

PATCH /brains/{id} · can_engine

ParameterTypeRequiredDescription
namestringNoNew name
creator_idstringNoLink it to another creator
curl -X PATCH https://api.lanachat.ai/v1/brains/br_lea_main \
  -H "Authorization: Bearer $LANACHAT_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{"name": "Lea · main FR"}'

The answer is the updated brain.

Delete a brain #

DELETE /brains/{id} · can_engine

curl -X DELETE https://api.lanachat.ai/v1/brains/br_lea_old \
  -H "Authorization: Bearer $LANACHAT_TOKEN"

A brain that an account still uses is refused (409): link those accounts to another brain first.

Drafts and publishing #

Read the draft #

GET /brains/{id}/draft · can_engine

curl https://api.lanachat.ai/v1/brains/br_lea_main/draft \
  -H "Authorization: Bearer $LANACHAT_TOKEN"

The answer is the current draft (phases, rules and settings) and what differs from the live version.

Change the draft #

PATCH /brains/{id}/draft · can_engine

ParameterTypeRequiredDescription
phasesarrayNoSales phases to change
rulesarrayNoRules to change
settingsobjectNoSettings to change, for example first_offer_after_messages or max_discount_percent
curl -X PATCH https://api.lanachat.ai/v1/brains/br_lea_main/draft \
  -H "Authorization: Bearer $LANACHAT_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{"settings": {"first_offer_after_messages": 6, "max_discount_percent": 20}}'

Only the fields you send change. The live brain does not move until you publish.

Throw the draft away #

DELETE /brains/{id}/draft · can_engine

curl -X DELETE https://api.lanachat.ai/v1/brains/br_lea_main/draft \
  -H "Authorization: Bearer $LANACHAT_TOKEN"

The draft is deleted; the live version stays as it is and has_draft becomes false.

Publish the draft #

POST /brains/{id}/publish · can_publish

curl -X POST https://api.lanachat.ai/v1/brains/br_lea_main/publish \
  -H "Authorization: Bearer $LANACHAT_TOKEN" \
  -H "Idempotency-Key: $(uuidgen)"
{ "id": "br_lea_main", "version": 13, "published_at": "2026-10-06T14:20:03Z", "has_draft": false }

The draft becomes live on every linked account. Publishing without a draft answers 409. Advanced AI profiles need their own owner permissions, as in the Console. A webhook brain.published tells your server.

Versions #

List versions #

GET /brains/{id}/versions · can_engine

curl https://api.lanachat.ai/v1/brains/br_lea_main/versions \
  -H "Authorization: Bearer $LANACHAT_TOKEN"

The answer lists the published versions, newest first, paginated.

Restore a version #

POST /brains/{id}/versions/{version}/restore · can_engine

curl -X POST https://api.lanachat.ai/v1/brains/br_lea_main/versions/11/restore \
  -H "Authorization: Bearer $LANACHAT_TOKEN" \
  -H "Idempotency-Key: $(uuidgen)"

The old version is copied into the draft. Nothing changes for fans until you publish. An unknown version answers 404.

Playground #

The Playground talks to the draft, never to a fan. Nothing is sent on Telegram and nothing is sold.

Send a test message #

POST /playground/{brain_id}/message · can_engine

ParameterTypeRequiredDescription
textstringYesWhat the test fan writes
fanobjectNoThe test fan: language (for example en) and is_new
curl -X POST https://api.lanachat.ai/v1/playground/br_lea_main/message \
  -H "Authorization: Bearer $LANACHAT_TOKEN" \
  -H "Idempotency-Key: $(uuidgen)" \
  -H "Content-Type: application/json" \
  -d '{"text": "hey, are you real?", "fan": {"language": "en", "is_new": true}}'
{
  "reply": { "text": "Haha very real, just slow at typing 🙈 where are you from?", "media": [] },
  "phase": "warm_up",
  "explain": "Phrase bank answer for \"Are you a bot?\", then a question to keep the fan talking."
}
  • reply is what the AI would send: text and media.
  • phase is the sales phase the AI is in.
  • explain says in plain English why it answered that way.

Each call continues the same test conversation.

Start the test conversation over #

DELETE /playground/{brain_id}/session · can_engine

curl -X DELETE https://api.lanachat.ai/v1/playground/br_lea_main/session \
  -H "Authorization: Bearer $LANACHAT_TOKEN"

The next test message starts a new conversation, as a new fan.

Latest news about Lana on Telegram

New releases and beta invites, first in the channel.