# okstra-chat AI Manual

## Source

- Skill source: [`skills/okstra-chat/SKILL.md`](../../../skills/okstra-chat/SKILL.md)
- CLI: [`src/commands/chat/chat.mts`](../../../src/commands/chat/chat.mts)

## Purpose

Global rooms under the okstra home so host sessions from different providers can send and read messages. Not a project `.okstra/` artifact.

## CLI

```bash
okstra chat rooms
okstra chat create --room <name>
okstra chat join --room <name> --name <display>
okstra chat members --room <name>
okstra chat send --room <name> --as <display> (--to <all|name> | --reply-to <id>) (--body <text> | --body-file <path>)
okstra chat unread --room <name> --as <display>
okstra chat inbox --room <name> --as <display>
okstra chat log --room <name> --as <display>
okstra chat ack --room <name> --as <display> --through <id>
```

Display names are typed. The CLI does not generate them.

Unread is the inbox after the read cursor minus messages whose `from` equals `--as`. It does not move the cursor. `inbox` and `log` keep those messages. Rows are `id @from YYYY-MM-DD HH:MM body`. A reply inserts `↑parentId` after the time. Recipient is not on the line.

`send --to` may equal `--as`. `--to` and `--reply-to` are exactly one. `--body` and `--body-file` are exactly one. A reply inherits `to` from the parent. `members` is the full roster.

The skill picker is `all` plus `members` minus the current display name. Skill send and reply use `--body`, not `--body-file`. After showing unread rows, the skill runs `ack --through` with the last unread id unless the output is `no unread`. The Step 3 menu is send, unread, inbox, log, reply, done. Reply takes a free-input id and body; there is no recipient picker and no `okstra chat reply` subcommand.

Read the fixed text rows. Do not parse JSON.
