# Sending messages

> Post, update and delete chat messages from your app with text, Block Kit blocks and attachments.

A message has three optional parts: `text`, `blocks` and `attachments`. Send at least one.

- **`text`** — plain text with [mrkdwn formatting](https://workstation.repzo.com/docs/developers/chat-apps/formatting-text). With `blocks`, it becomes the notification and search fallback, as on Slack.
- **`blocks`** — up to 50 [Block Kit blocks](https://workstation.repzo.com/docs/developers/block-kit/blocks). This is what people see.
- **`attachments`** — Slack's legacy [secondary attachments](https://workstation.repzo.com/docs/developers/block-kit/objects/attachment-object) with a coloured side bar, shown after the blocks.

## Post a message

```http
POST /api/bot/chat.postMessage
Authorization: Bearer foxa-…
Content-Type: application/json
```

```json
{
  "channel": "support",
  "text": "Ticket #4821 was escalated",
  "blocks": [
    { "type": "header", "text": { "type": "plain_text", "text": "Ticket #4821 escalated" } },
    {
      "type": "section",
      "fields": [
        { "type": "mrkdwn", "text": "*Customer*\nAcme Ltd" },
        { "type": "mrkdwn", "text": "*Priority*\nUrgent" }
      ]
    }
  ]
}
```

| Field | Description |
|---|---|
| `channel` | Channel id or short name. Required. |
| `text` | Message text, or the fallback when `blocks` are sent. |
| `blocks` | Array of blocks, or the same array as a JSON string (form-encoded requests). |
| `attachments` | Array of attachments, or a JSON string. |
| `thread_ts` | Reply in a thread: the parent message's `ts`. |
| `idempotency_key` | Or the `Idempotency-Key` header. Retrying with the same key returns the first message instead of posting twice. |

The answer follows Slack:

```json
{
  "ok": true,
  "ts": "3a77c808-55af-410c-aac3-32f02c0c782f",
  "channel": "e0fd46e9-86de-4104-a1d0-f7a1ed30f403",
  "message": { "text": "Ticket #4821 was escalated", "ts": "3a77c808-…", "bot_id": "75385d0c-…", "blocks": [ … ] }
}
```

`ts` is the message id: keep it to update, delete or reply to the message.

> **Differs from Slack**
>
> Message ids (`ts`) are UUIDs, not timestamps. Treat them as opaque strings.

## Warnings, never rejections

Workstation never rejects a message because of its blocks. Missing `block_id` / `action_id` values are generated, unsupported blocks are skipped, and anything that doesn't match the Block Kit rules is reported back in `response_metadata.warnings` (bot API) or `warnings` (REST API) so you can fix it:

```json
{
  "ok": true,
  "ts": "…",
  "response_metadata": {
    "warnings": ["blocks[1].elements[0].text: longer than 75 characters"]
  }
}
```

## Update and delete

```http
POST /api/bot/chat.update
```

```json
{ "ts": "3a77c808-…", "text": "Ticket #4821 resolved", "blocks": [ … ] }
```

Sending `blocks` or `attachments` replaces them; sending only `text` replaces the whole message with that text. People see the edit immediately. Delete with `POST /api/bot/chat.delete` and `{ "ts": "…" }`. An app can only edit and delete its own messages.

## Using the REST API instead

The same messages through the [REST API](https://workstation.repzo.com/api/v1/docs):

```http
POST /api/v1/chat/channels/{channelId}/messages
```

```json
{
  "body": "Ticket #4821 was escalated",
  "blocks": [ … ],
  "attachments": [ … ],
  "parentMessageId": "…",
  "clientMessageId": "9b2f…"
}
```

`PATCH /api/v1/chat/messages/{id}` takes `body`, `blocks` and `attachments`; `DELETE /api/v1/chat/messages/{id}` deletes. The REST API needs the `chat_messages:write` scope.

## Errors

| `error` | Meaning |
|---|---|
| `channel_not_found` | No such channel, or the bot can't post there (private channel it isn't in, or not on its allowlist). |
| `is_archived` | The channel is archived. |
| `not_in_channel` | An AI-agent bot must be a member of the channel. |
| `no_text` | No `text`, `blocks` or `attachments`. |
| `message_not_found` | `chat.update` / `chat.delete` on a message that isn't the bot's or no longer exists. |
| `missing_scope` | The bot lacks a scope; `needed` names it. |

## Related

- [Block Kit reference](https://workstation.repzo.com/docs/developers/block-kit)
- [Formatting text](https://workstation.repzo.com/docs/developers/chat-apps/formatting-text)
- [Interactivity](https://workstation.repzo.com/docs/developers/chat-apps/interactivity)
