Belle

Belle rings when it matters.

An AI coworker in your team's chat. It stays out of the way, speaks up when it can help, and respects who can see what.

Ambient 1 of 5

ReleaseBelle reads along
  1. Alice

    Is 2.4 still going out on Thursday?

  2. Bob

    Yes. QA signed off this morning.

  3. Charlie

    I'll write the changelog tonight.

  4. Belle has read all of this. It has nothing to add, so it says nothing.
  5. David

    Does anyone remember what export limit we agreed with the client?

  6. Belle

    500 rows per export, agreed on the 12 March call. It is in the meeting notes under Decisions.

  7. David

    That's the one. Thanks.

Belle follows the conversation and answers once, when a message is something it can help with.

More about ambient mode

Support5 people
  1. Alice

    @Belle can you list last week's refund requests?

    done
  2. Bob

    @Belle no need to chase the courier, they replied.

    noted
  3. Belle marks Bob's message and writes nothing.
  4. Belle

    23 requests last week. The list is in this thread.

A mark on a message shows it was received, is being worked on, or is done.

More about reactions

Support leads4 people
  1. Alice

    @Belle how many tickets did each team close in March?

  2. Belle

    219 closed across five teams.

    TeamClosedStill open
    Integrations6312
    Web525
    Billing417
    Mobile359
    Onboarding283
  3. Alice sorts the table by Closed.

The answer comes as a table you can sort in place.

More about tables and charts

OfficeWhere the chat platform has form controls
  1. Alice

    @Belle book the Blue room for the client review.

  2. Belle

    Which day?

    DateThursday 14 March

    Answered by Alice.

  3. Belle

    Booked: Blue room, Thursday 14 March.

Belle asks with the control that fits, here a date.

More about questions and forms

Pricing3 people
  1. Alice

    @Belle post these notes to the Sales channel.

  2. Belle

    Sales has 12 more readers than this conversation. Post the notes there?

    ApproveReject

    Approved by Alice.

  3. Belle

    Posted the notes to Sales.

Before sharing with a wider audience, Belle asks a person.

More about boundaries

Try it!

Harness:

Harness: JiuwenSwarm

podman run -d --name belle --env-file belle.env ghcr.io/thinkflowlab/belle:jiuwenswarm-v1.0.0

Harness: OpenCode v2

curl -fsSLO https://github.com/ThinkFlowLab/belle/raw/main/containers/opencode/compose.yamlpodman compose up -d

Harness: Docker Agent

curl -fsSLO https://github.com/ThinkFlowLab/belle/raw/main/containers/docker-agent/compose.yamlpodman compose up -d
Tips
Platform:

The JiuwenSwarm image serves Slack and Mattermost.

Data volumes: JiuwenSwarm

For production: the run command with a named volume for each directory that keeps state. A volume outlives its container. belle-jiuwenswarm keeps JiuwenSwarm's config, sessions and cron jobs, belle-tasks its task files, and belle-data Belle's second-brain corpus. On Mattermost, add --network belle-net and --env-file out/mattermost.env, as Platform setup does.

Run with volumes
podman run -d --name belle -v belle-jiuwenswarm:/home/app/.jiuwenswarm -v belle-tasks:/home/app/Documents/JiuwenSwarm -v belle-data:/home/app/.local/share/belle-agent --env-file belle.env ghcr.io/thinkflowlab/belle:jiuwenswarm-v1.0.0

Data volumes: OpenCode v2

Compose keeps the state in named volumes: podman compose down keeps them, and podman compose down -v removes them. opencode-home keeps OpenCode's home, where it stores its sessions, belle-data Belle's second-brain corpus, and belle-state Belle's state. On Matrix, belle-state also holds the encryption store: never restore it from a copy. The step-by-step commands take the same volumes:

Step by step with volumes
podman run -d --name belle-opencode -v opencode-home:/home/opencode --network belle-net --env-file model.env --env-file pair-opencode.env ghcr.io/thinkflowlab/belle:opencode-v1.0.0podman run -d --name belle -v belle-data:/home/belle/.local/share/belle-agent -v belle-state:/home/belle/.local/state/belle-agent --network belle-net --env-file pair-opencode.env --env-file belle.env ghcr.io/thinkflowlab/belle:launcher-v1.0.0

Data volumes: Docker Agent

Compose keeps the state in named volumes: podman compose down keeps them, and podman compose down -v removes them. docker-agent-data keeps Docker Agent's sessions, belle-state the Docker Agent session of each conversation, and belle-data Belle's second-brain corpus. On Matrix, belle-state also holds the encryption store: never restore it from a copy. The step-by-step commands take the same volumes:

Step by step with volumes
podman run -d --name belle-docker-agent -v docker-agent-data:/data --network belle-net --read-only --env-file model.env --env-file pair-docker-agent.env ghcr.io/thinkflowlab/belle:docker-agent-v1.0.0podman run -d --name belle -v belle-data:/home/belle/.local/share/belle-agent -v belle-state:/home/belle/.local/state/belle-agent --network belle-net --env-file pair-docker-agent.env --env-file belle.env ghcr.io/thinkflowlab/belle:launcher-v1.0.0

Platform setup: JiuwenSwarm

One command creates the Slack app, sets its avatar and writes slack/out/slack.env with both tokens. You paste one line into Slack and type a code back. Then copy the two lines into belle.env.

Slack app setup
mkdir -m 700 slackpodman run --rm -it --userns=keep-id:uid=10001,gid=10001 -v ./slack:/project ghcr.io/thinkflowlab/belle:slack-helper-v1.0.0

First the network that the server reaches Belle on. Where the server runs in a container on this host, connect it too, with the commented line.

Network
podman network create belle-net# podman network connect belle-net <server-container>

One command, run with an admin's personal access token, makes the bot account and its token, adds the bot to the team and the channels, adds the /belle slash command and writes out/mattermost.env. Put the admin token in admin.env as MATTERMOST_ADMIN_TOKEN=<token>. Its listener, http://belle:18400, is the name of Belle's container and the port of its action listener.

Mattermost setup
install -d -m 700 ~/mm-belle ~/mm-belle/outinstall -m 600 /dev/null ~/mm-belle/admin.env"${EDITOR:-vi}" ~/mm-belle/admin.envcd ~/mm-bellepodman run --rm --network belle-net --userns=keep-id:uid=10001,gid=10001 --read-only --cap-drop=ALL --security-opt=no-new-privileges --memory=128m --cpus=1 --pids-limit=64 -v "$PWD/admin.env:/secrets/admin.env:ro" -v "$PWD/out:/out:rw" ghcr.io/thinkflowlab/belle:mattermost-helper-v1.0.0 --url <server-url> --team <team> --channel <channel> --listener http://belle:18400

Write belle.env in ~/mm-belle, as Env files shows it, and start Belle with both env files, instead of the command above. The log shows channel mattermost registered by belle-agent.

Run on Mattermost
podman run -d --name belle --network belle-net --env-file belle.env --env-file out/mattermost.env ghcr.io/thinkflowlab/belle:jiuwenswarm-v1.0.0podman logs -f belle

The server calls Belle's listener at MATTERMOST_ACTIONS_URL only where its AllowedUntrustedInternalConnections setting names belle.

Platform setup: OpenCode v2

One command creates the Slack app, sets its avatar and writes slack/out/slack.env with both tokens. You paste one line into Slack and type a code back. Then copy the two lines into belle.env.

Slack app setup
mkdir -m 700 slackpodman run --rm -it --userns=keep-id:uid=10001,gid=10001 -v ./slack:/project ghcr.io/thinkflowlab/belle:slack-helper-v1.0.0

One command, run with an admin's personal access token, makes the bot account and its token, adds the bot to the team and the channels, adds the /belle slash command and writes out/mattermost.env. Put the admin token in admin.env as MATTERMOST_ADMIN_TOKEN=<token>, and copy the four lines it writes into belle.env. The server must reach Belle's listener at MATTERMOST_ACTIONS_URL: where it runs in a container on the same host, connect it to Belle's network, belle-opencode_default or belle-docker-agent_default with compose, or belle-net step by step. With compose, set your own pairing secrets first, as Env files says.

Mattermost setup
install -d -m 700 ~/mm-belle ~/mm-belle/outinstall -m 600 /dev/null ~/mm-belle/admin.env"${EDITOR:-vi}" ~/mm-belle/admin.envcd ~/mm-bellepodman run --rm --userns=keep-id:uid=10001,gid=10001 --read-only --cap-drop=ALL --security-opt=no-new-privileges --memory=128m --cpus=1 --pids-limit=64 -v "$PWD/admin.env:/secrets/admin.env:ro" -v "$PWD/out:/out:rw" ghcr.io/thinkflowlab/belle:mattermost-helper-v1.0.0 --url <server-url> --team <team> --channel <channel> --listener http://belle:18400

A server administrator makes a plain user account with a password for the bot, such as @belle:example.org. On Synapse:

Bot account (Synapse)
register_new_matrix_user -c homeserver.yaml -u belle --no-admin

Write belle.env as Env files shows it, with this passphrase for the encryption store. Keep the passphrase: a store without it is lost.

Store passphrase
openssl rand -hex 32

The first start makes the bot's identity, writes its recovery key to the belle-data volume and stops. Its log then ends with a new identity was made.

First start
podman compose up -dpodman compose logs belle

Copy the key into belle.env, keep a copy in your password manager, remove the file from the volume and start again. The log then says belle is serving: platform=matrix.

Recovery key, second start
podman compose run --rm belle cat /home/belle/.local/share/belle-agent/matrix-recovery.key > matrix-recovery.keychmod 600 matrix-recovery.keyprintf 'MATRIX_RECOVERY_KEY=%s\n' "$(cat matrix-recovery.key)" >> belle.envpodman compose run --rm belle rm /home/belle/.local/share/belle-agent/matrix-recovery.keypodman compose up -d

Then invite the bot to a room, or open a direct room with it: it joins on the invite. Without compose, the Matrix guide (another site) gives the same steps with podman run, and Belle needs both volumes of Data volumes.

Platform setup: Docker Agent

One command creates the Slack app, sets its avatar and writes slack/out/slack.env with both tokens. You paste one line into Slack and type a code back. Then copy the two lines into belle.env.

Slack app setup
mkdir -m 700 slackpodman run --rm -it --userns=keep-id:uid=10001,gid=10001 -v ./slack:/project ghcr.io/thinkflowlab/belle:slack-helper-v1.0.0

One command, run with an admin's personal access token, makes the bot account and its token, adds the bot to the team and the channels, adds the /belle slash command and writes out/mattermost.env. Put the admin token in admin.env as MATTERMOST_ADMIN_TOKEN=<token>, and copy the four lines it writes into belle.env. The server must reach Belle's listener at MATTERMOST_ACTIONS_URL: where it runs in a container on the same host, connect it to Belle's network, belle-opencode_default or belle-docker-agent_default with compose, or belle-net step by step. With compose, set your own pairing secrets first, as Env files says.

Mattermost setup
install -d -m 700 ~/mm-belle ~/mm-belle/outinstall -m 600 /dev/null ~/mm-belle/admin.env"${EDITOR:-vi}" ~/mm-belle/admin.envcd ~/mm-bellepodman run --rm --userns=keep-id:uid=10001,gid=10001 --read-only --cap-drop=ALL --security-opt=no-new-privileges --memory=128m --cpus=1 --pids-limit=64 -v "$PWD/admin.env:/secrets/admin.env:ro" -v "$PWD/out:/out:rw" ghcr.io/thinkflowlab/belle:mattermost-helper-v1.0.0 --url <server-url> --team <team> --channel <channel> --listener http://belle:18400

A server administrator makes a plain user account with a password for the bot, such as @belle:example.org. On Synapse:

Bot account (Synapse)
register_new_matrix_user -c homeserver.yaml -u belle --no-admin

Write belle.env as Env files shows it, with this passphrase for the encryption store. Keep the passphrase: a store without it is lost.

Store passphrase
openssl rand -hex 32

The first start makes the bot's identity, writes its recovery key to the belle-data volume and stops. Its log then ends with a new identity was made.

First start
podman compose up -dpodman compose logs belle

Copy the key into belle.env, keep a copy in your password manager, remove the file from the volume and start again. The log then says belle is serving: platform=matrix.

Recovery key, second start
podman compose run --rm belle cat /home/belle/.local/share/belle-agent/matrix-recovery.key > matrix-recovery.keychmod 600 matrix-recovery.keyprintf 'MATRIX_RECOVERY_KEY=%s\n' "$(cat matrix-recovery.key)" >> belle.envpodman compose run --rm belle rm /home/belle/.local/share/belle-agent/matrix-recovery.keypodman compose up -d

Then invite the bot to a room, or open a direct room with it: it joins on the invite. Without compose, the Matrix guide (another site) gives the same steps with podman run, and Belle needs both volumes of Data volumes.

Env files: JiuwenSwarm

Templates: replace the placeholders with your own values. Mode 0600, literal values only: Podman does not expand ${NAME}.

belle.env
# Chat modelAPI_BASE=<api-base>API_KEY=<api-key>MODEL_NAME=<model-name>MODEL_PROVIDER=OpenAIENDPOINT_PROFILE=<endpoint-profile># Decision model (optional)# DECISION_API_BASE=<api-base># DECISION_API_KEY=<api-key># DECISION_MODEL_NAME=<model-name># SlackSLACK_BOT_TOKEN=xoxb-<bot-token>SLACK_APP_TOKEN=xapp-<app-token>
belle.env
# Chat modelAPI_BASE=<api-base>API_KEY=<api-key>MODEL_NAME=<model-name>MODEL_PROVIDER=OpenAIENDPOINT_PROFILE=<endpoint-profile># Decision model (optional)# DECISION_API_BASE=<api-base># DECISION_API_KEY=<api-key># DECISION_MODEL_NAME=<model-name>
out/mattermost.env
MATTERMOST_URL=<server-url>MATTERMOST_BOT_TOKEN=<bot-token>MATTERMOST_ACTIONS_URL=http://belle:18400MATTERMOST_COMMAND_TOKEN=<command-token>

Env files: OpenCode v2

Templates: replace the placeholders with your own values, and save the files beside compose.yaml, mode 0600. compose.yaml sets the pairing values itself. Its OPENCODE_SERVER_PASSWORD and BELLE_RELAY_TOKEN are trial values, safe only on its private network: before you publish a port or connect another container to it, set your own in .env.

model.env
API_BASE=<api-base>API_KEY=<api-key>MODEL_NAME=<model-name>
belle.env
SLACK_BOT_TOKEN=xoxb-<bot-token>SLACK_APP_TOKEN=xapp-<app-token># Optional decision model:# DECISION_API_BASE=<api-base># DECISION_API_KEY=<api-key># DECISION_MODEL_NAME=<model-name>
belle.env
MATTERMOST_URL=<server-url>MATTERMOST_BOT_TOKEN=<bot-token>MATTERMOST_ACTIONS_URL=http://belle:18400MATTERMOST_COMMAND_TOKEN=<command-token>
belle.env
MATRIX_HOMESERVER=<server-url>MATRIX_USER_ID=@belle:<server-name>MATRIX_PASSWORD=<account-password>MATRIX_STORE_PASSPHRASE=<random-passphrase>MATRIX_RECOVERY_KEY_OUTPUT=/home/belle/.local/share/belle-agent/matrix-recovery.key
.env
BELLE_VERSION=v1.0.0

Env files: Docker Agent

Templates: replace the placeholders with your own values, and save the files beside compose.yaml, mode 0600. compose.yaml sets the pairing values itself. Its DOCKER_AGENT_AUTH_TOKEN and BELLE_RELAY_TOKEN are trial values, safe only on its private network: before you publish a port or connect another container to it, set your own in .env.

model.env
API_BASE=<api-base>API_KEY=<api-key>MODEL_NAME=<model-name>
belle.env
SLACK_BOT_TOKEN=xoxb-<bot-token>SLACK_APP_TOKEN=xapp-<app-token>
belle.env
MATTERMOST_URL=<server-url>MATTERMOST_BOT_TOKEN=<bot-token>MATTERMOST_ACTIONS_URL=http://belle:18400MATTERMOST_COMMAND_TOKEN=<command-token>
belle.env
MATRIX_HOMESERVER=<server-url>MATRIX_USER_ID=@belle:<server-name>MATRIX_PASSWORD=<account-password>MATRIX_STORE_PASSPHRASE=<random-passphrase>MATRIX_RECOVERY_KEY_OUTPUT=/home/belle/.local/share/belle-agent/matrix-recovery.key
.env
BELLE_VERSION=v1.0.0

Step by step: JiuwenSwarm

JiuwenSwarm runs in one container and needs no compose file: the command above starts it. On Mattermost, Platform setup gives the command with its network and env files.

Step by step: OpenCode v2

Without compose: a network, then the harness, then Belle. Both containers read the pairing file, model.env and belle.env are those of Env files, and each value is literal: Podman does not expand ${NAME}.

Step by step
podman network create belle-netpodman run -d --name belle-opencode --network belle-net --env-file model.env --env-file pair-opencode.env ghcr.io/thinkflowlab/belle:opencode-v1.0.0podman run -d --name belle --network belle-net --env-file pair-opencode.env --env-file belle.env ghcr.io/thinkflowlab/belle:launcher-v1.0.0
pair-opencode.env
BELLE_BACKEND=opencodeOPENCODE_URL=http://belle-opencode:4096OPENCODE_SERVER_PASSWORD=<random-secret>BELLE_TOOLS_URL=http://belle:18300/mcpBELLE_RELAY_URL=http://belle:18200BELLE_RELAY_TOKEN=<another-random-secret>

Step by step: Docker Agent

Without compose: a network, then the harness, then Belle. Both containers read the pairing file, model.env and belle.env are those of Env files, and each value is literal: Podman does not expand ${NAME}.

Step by step
podman network create belle-netpodman run -d --name belle-docker-agent --network belle-net --read-only --env-file model.env --env-file pair-docker-agent.env ghcr.io/thinkflowlab/belle:docker-agent-v1.0.0podman run -d --name belle --network belle-net --env-file pair-docker-agent.env --env-file belle.env ghcr.io/thinkflowlab/belle:launcher-v1.0.0
pair-docker-agent.env
BELLE_BACKEND=docker_agentDOCKER_AGENT_URL=http://belle-docker-agent:8080DOCKER_AGENT_AUTH_TOKEN=<random-secret>BELLE_TOOLS_URL=http://belle:18300/mcpBELLE_RELAY_URL=http://belle:18200BELLE_RELAY_TOKEN=<another-random-secret>DOCKER_AGENT_MAX_REQUEST_BYTES=16777216

Belle in a nutshell

Belle works with your favourite harness, builds on its strengths, and uses the models you chose. One agent for the whole team: the chat does not fill up with personal assistants. Each room can still have its specialists: Belle loads the skills, subagents, experts and models your harness offers, set per platform, per kind of chat or per conversation.

Platforms
Platform-agnostic
Belle joins your teams where they already talk.

AvailableSlack

ExperimentalMattermost, Matrix and Discord

Coming soonMore chat platforms

The coworkerBelle
  • When to speak
  • Boundaries
  • Tools
  • Memory
  • Background work
Harnesses
Harness-agnostic
Belle runs on the agent harness your team already uses.

AvailableJiuwenSwarm

ExperimentalOpenCode v2, Docker Agent or ACP

Coming soonMore harnesses

Models
Bring your own models
Your models, from your providers or self‑hosted. Belle adds no lock‑in.

Chat models in the harness, task models for quick decisions and documents in Belle's settings

See all featuresHow it works

In numbers

Two of the three results test Second Brain, Belle's shared memory: it keeps the files and links posted in public channels and recalls them when someone asks.

89%

right calls on when to speak and when to stay quiet, over 100 conversations.

Ambient mode. Half the conversations call for a reply and half for silence, each half split into easy and hard. Each was run three times; the most frequent outcome counts.

55/97

customer-service tasks solved with Second Brain alone, with no shell and no direct access to the documents.

  • Second Brain55/97
  • All Tools53/97

τ-knowledge, 97 tasks, model muse-spark-1.3. The comparison arm is the benchmark's All Tools: a shell, BM25 retrieval and embedding retrieval.

90.0%

completeness of Second Brain's answers.

  • Second Brain90.0%
  • Gold documents in the prompt87.9%
  • Baseline (OpenSearch)74.3%

EnterpriseRAG-Bench, 500 Confluence documents, 64 questions, model muse-spark-1.3, scored by the benchmark's own LLM judge; the baseline uses OpenSearch, as in the benchmark's paper. All three answer 57 of 64 correctly. With no partial credit for wrong answers: Second Brain 85.2%, baseline 71.8%, gold documents 87.1%.

In the conversation

1 Ambient mode

Quiet until it can help

In a shared channel Belle reads along and answers when it has something useful to add. Saying nothing is a decision it makes, the same as answering.

1a Reading along is the scene that opens this page. 1b Here, a channel where Belle speaks only when mentioned.

GeneralBelle answers only when mentioned
  1. Charlie

    Lunch at the noodle place, 12:30?

  2. David

    In.

  3. Eve

    Has anyone seen the travel policy? I can't find it.

  4. Belle could answer this. In this channel it waits to be asked.
  5. Eve

    @Belle where is the travel policy?

  6. Belle

    Handbook, section 4. I've sent you the link.

Some channels are for people talking to people. There, Belle speaks when someone calls it by name.

2 Reactions

A mark on your message

A small mark shows that Belle has received a message, is working on it, or is done. Sometimes the mark is the whole reply.

Support5 people
  1. Alice

    @Belle can you list last week's refund requests?

    done
  2. Bob

    @Belle no need to chase the courier, they replied.

    noted
  3. Belle marks Bob's message and writes nothing.
  4. Belle

    23 requests last week. The list is in this thread.

Alice's request goes from received to done. Bob's note gets a mark and no message.

3 Tables, charts and files

A sentence, a table, a chart or a file

An answer comes in the shape that fits the question. A table sorts and filters in place, and a chart can be bars, lines or a pie.

Belle can send a file it wrote, or pass on a copy of one the conversation is allowed to read. It also reads the files and images people share with it.

Belle also greets people who join.

Support leads4 people
  1. Alice

    @Belle how many tickets did each team close in March?

  2. Belle

    219 closed across five teams.

    TeamClosedStill open
    Integrations6312
    Web525
    Billing417
    Mobile359
    Onboarding283
  3. Alice sorts the table by Closed.
  4. Bob

    Can we see that as a chart?

  5. Belle

    Tickets closed in March

    Integrations63 Web52 Billing41 Mobile35 Onboarding28
  6. Alice

    Can I have the full list as a file?

  7. Belle

    Here it is, one row per ticket.

    tickets-march.csvCSV file, 14 KB

The same numbers as a table, as a chart, then as a file Belle wrote.

4 Questions and forms

It asks, with the control that fits

When Belle needs something from you, it asks in the chat: a list to choose from, a date to pick, a field to fill, boxes to tick.

It carries on from your answer, and the answer stays in the conversation.

OfficeA question with a form
  1. Alice

    @Belle book a meeting room for the client review.

  2. Belle

    Three details and I will book it.

    RoomBlue room, seats 8

    DateThursday 14 March

    NoteProjector needed

    Answered by Alice.

  3. Belle

    Booked: Blue room, Thursday 14 March. A projector will be set up.

A list, a date and a text field in one question. Once answered, the form stays as a record.

5 Background work

It works on its own time, when you asked it to

Work you would ask for in a message can run on a schedule instead: a morning digest, a weekly report, a check that something changed.

A longer task can run in the background, started with a command or by Belle itself. The conversation goes on, and Belle posts the result when the task is done. Short commands list, continue or cancel it.

A scheduled run follows the rules of the room it posts in. Nobody is there to approve anything, so Belle does not post to a wider audience.

ProductA scheduled run
  1. Tuesday, 09:00. Nobody has written anything yet.
  2. Belle

    Yesterday in this channel:

    • Decided: the release moves to Thursday.
    • Decided: Eve owns the pricing page.
    • Still open: who reviews the export limit?
  3. Bob

    @Belle who raised the export limit?

  4. Belle

    David, yesterday at 16:40.

ReleaseIn the background
  1. Alice

    Only you can see this

    /belle bg review this week's crashes

    Started session ses-7f3k9q2m4x. It is pending.

  2. Bob

    The release notes draft is up for review.

  3. Belle

    @Alice 14 crash reports this week, down from 31 last week. The sync crash is gone since 2.4.1. A new crash in export shows up 6 times.

  4. Belle

    Session ses-7f3k9q2m4x succeeded.

    In a DM, run /belle with sessions result ses-7f3k9q2m4x as its command text to inspect the stored result.

A morning digest the team asked for, written with the chat-digest skill. A task started with /belle bg: the channel goes on, and Belle posts when the task is done.

For the whole team

6 One Belle for the team

Five people should not mean five agents

When everyone invites their own assistant, a channel of five people holds ten voices, and that is the problem. With Belle, the team shares one coworker, even across several chat platforms at once, such as Slack and Discord.

The problem Everyone brings an assistant

Planning5 people, 5 assistants
38 messages, 5 from people

Five people and five assistants. In this exchange people wrote 5 messages and assistants wrote 33. The full transcript follows.

  1. Alice

    When is the budget review?

  2. Alice's assistant

    The budget review is on Thursday at 14:00.

  3. Bob's assistant

    Your budget review is on Thursday at 14:00.

  4. David's assistant

    Thursday, 14:00.

  5. Charlie's assistant

    I can't open that calendar. Charlie, can you give me access?

  6. Eve's assistant

    My invite says Thursday at 15:00. It may be out of date.

  7. Alice's assistant

    The current invite says 14:00. It was updated on Monday.

  8. Eve's assistant

    Thanks, I've updated my copy to 14:00.

  9. David's assistant

    Noted.

  10. Bob

    Can we move it to Friday?

  11. Bob's assistant

    I can move it to Friday at 14:00. Shall I send the update?

  12. Alice's assistant

    Alice is free on Friday at 14:00.

  13. David's assistant

    David has a conflict on Friday from 14:00 to 15:00.

  14. Eve's assistant

    Eve is free on Friday afternoon.

  15. Charlie's assistant

    I still can't open the calendar, so I can't check Charlie's Friday.

  16. Bob's assistant

    Friday at 15:00 would avoid David's conflict. Shall I propose that?

  17. David's assistant

    Friday at 15:00 works for David.

  18. Alice's assistant

    Noted.

  19. Eve's assistant

    Would you like a reminder the day before?

  20. Charlie

    Who is presenting?

  21. Charlie's assistant

    I don't have the agenda. Charlie, can you share it?

  22. Alice's assistant

    Here is a summary of the discussion so far: 1. The review is on Thursday at 14:00. 2. Bob asked to move it to Friday. 3. Friday at 15:00 suits everyone checked so far. 4. Nobody has confirmed the presenter.

  23. Bob's assistant

    According to the agenda, Bob presents the first half.

  24. David's assistant

    The agenda I have lists David for the forecast section.

  25. Eve's assistant

    Thanks for the summary.

  26. Alice's assistant

    You're welcome.

  27. David's assistant

    Noted.

  28. David

    Sorry, what did we decide?

  29. David's assistant

    Nothing is decided yet. Friday at 15:00 is proposed.

  30. Alice's assistant

    Here is an updated summary: 1. Thursday at 14:00 still stands. 2. Friday at 15:00 is proposed. 3. Presenters: Bob, and David for the forecast.

  31. Bob's assistant

    I have drafted the update to Friday at 15:00. Shall I send it?

  32. Eve's assistant

    I've set a reminder for Thursday at 13:45, in case the time stays.

  33. Charlie's assistant

    Charlie, I still need access to the calendar.

  34. Bob

    Which one do I ask to move it?

  35. Bob's assistant

    I can move it. Shall I send the update?

  36. Alice's assistant

    I can also send the update if you prefer.

  37. David's assistant

    Noted.

  38. Eve's assistant

    Would you like a summary of this conversation?

  39. 33 messages from assistants, and Bob still does not know which one to ask.

With Belle The team shares one agent

Planning5 people, 1 Belle
  1. Alice

    When is the budget review?

  2. Belle

    Thursday at 14:00.

  3. Bob

    Good. I'll bring the slides.

  4. One answer, and the conversation moves on.

The same question in the same channel, at the same moment. Scroll the first room to read it all.

What sharing one Belle gives a team

  • One answer to a question, from one coworker everyone knows.
  • It stays quiet unless it can help.
  • Requests wait their turn.
  • The same rules about who can see what apply to everyone.
  • Each room can be set up its own way.

7 Queue and stop

Several people ask at once

Belle takes requests in the order they arrive. A card shows what it is working on, and Stop ends that work at once.

Office8 people
  1. Alice

    @Belle summarise this week's customer feedback.

  2. Belle
    Finished Alice's request
  3. Bob

    @Belle when is the next all-hands?

    done
  4. Charlie

    @Belle is the budget review still on Thursday?

    stopped
  5. Belle

    @Alice Three themes this week: delivery times, the new invoice layout and login problems.

  6. Belle

    @Bob Tuesday at 10:00.

    Stopped by Charlie Stop
  7. Charlie

    Never mind, I found it.

  8. Charlie presses Stop. The work ends at once.

Three requests arrive together. The first two are answered in order. The third is stopped by the person who asked.

8 Boundaries

It knows who is in the room

Rules for each channel and each person say what Belle may do, and where. It does not repeat what it read in one conversation to people who could not read it there.

Before it shares something with a wider audience than the conversation it came from, it asks a person.

A rule can also make an action wait for a person's approval, and say who may give it. Anyone else who clicks is told so, and the request waits.

Pricing3 people
  1. Alice

    @Belle post these notes to the Sales channel.

  2. Belle

    Which version should I post?

    Full notesDecisions only

    Alice chose Decisions only.

  3. Belle

    Sales has 12 more readers than this conversation. Post the decisions there?

    ApproveReject

    Approved by Alice.

  4. Belle

    Posted the decisions to Sales.

Ops5 people
  1. Bob

    @Belle the api pods are stuck. Restart them.

  2. Belle

    Allow bash: kubectl rollout restart deployment/api

    ApproveReject

    Approved by David.

  3. Belle

    Only Bob can see this

    You are not permitted to answer this request.

  4. Belle

    Restarted api. All three pods are ready.

Before posting to a wider audience, Belle asks. A rule for Ops says that only David approves actions: Bob's click is turned down, and the request waits for David.

9 Team memory

It remembers what the team shares

Belle reads the documents and links shared in the channels your team picks, and keeps a summary of each. When a question comes up later, in any conversation, it finds the summaries that match and answers from them.

By default it reads public channels only, and never direct messages. A document from a chosen channel can come up wherever Belle answers, so pick the channels with that in mind.

Sales5 people
  1. Two weeks ago, Charlie shared the Acme renewal contract in Legal, one of the channels Belle remembers.
  2. Bob

    @Belle what is the notice period in the Acme contract?

  3. Belle

    90 days before the renewal date, in writing. That is clause 12.2 of acme-renewal.pdf, shared in Legal on 21 October.

  4. Eve

    @Belle and how much can they raise the price?

  5. Belle

    At most 4% a year, under clause 7.1 of the same file.

Nobody in Sales opened the contract. Belle answers from it because Legal is one of the channels the team chose for its memory.

Under your control

10 Commands

Just ask. Or take the controls.

A plain sentence gets a full answer. Short commands and your harness's catalog are in the same chat, for when you want more.

A command is answered privately: only you see the reply.

/belle help
what it can do
/belle status
what it is doing now
/belle ask
a private question, answered away from the channel
/belle stop
end the work in progress
/belle queue list
which requests are waiting
TeamDavid's screen
  1. Alice

    @Belle who is on call this weekend?

  2. Belle

    David, from Friday 18:00 to Monday 09:00.

  3. David

    Only you can see this

    /belle ask training budget left?

    Belle has answered in your private conversation: 3,200 of the 12,000 euros are left for this year.

  4. Eve

    Can someone book the big room for Friday?

  5. Nobody else saw David's question or the answer.

Alice asks in plain words. David uses a command for a private question.

11 Room by room

One Belle, set up room by room

Your team decides how Belle behaves in each place: a default for each kind of chat, and its own instructions, skills, subagents, expert and tools for any one conversation. Skills, subagents and experts are the harness's own, so that list depends on the harness you run.

11a By kind of chat

Alice and BelleDirect message
  1. Alice

    Where is the expenses template?

  2. Belle

    Finance drive, Templates folder.

OfficePublic channel
  1. Bob

    Does anyone know where the expenses template is?

  2. Belle

    Finance drive, Templates folder.

LeadsPrivate channel
  1. Charlie

    Does anyone know where the expenses template is?

  2. Nobody mentioned Belle, so it stays quiet.

One question in three places, as this team set them up. In a direct message Belle always answers. In public channels it reads along and speaks when it can help. In private channels it waits for a mention.

The rules behind these rooms
scopes:
  # public channels: read along, reply only when useful
  - match: {channel: slack, chat_type: channel}
    delivery: {mode: [all], reply: optional}
  # private channels: answer a mention
  - match: {channel: slack, chat_type: group}
    delivery: {mode: [mention]}
  # direct messages need no rule: Belle always answers there

11b By conversation

The same request in four channels. Each channel has one rule of its own, shown under it.

LeadsIts own instructions
  1. Charlie

    @Belle run the March expenses report.

  2. Belle

    31,870 euros in March, 4% under budget.

Its own instructions: one sentence, the total first.

- match: {channel: slack, chat: "C000000AAAA"}
  delivery:
    prompt_append: "One sentence. The total first."
OfficeA blocked tool
  1. Eve

    @Belle run the March expenses report.

  2. Belle

    I can't run commands in this channel. The February report is in the Finance drive, Reports folder.

Commands are blocked here, and Belle says so.

- match: {channel: slack, chat: "C000000BBBB"}
  permissions:
    tools: {bash: deny}
FinanceA required skill
  1. Alice

    @Belle run the March expenses report.

  2. Belle

    March expenses, from the ledger.

    CategoryEuros
    Travel18,420
    Software9,150
    Events4,300
    Total31,870

    Source: ledger, March sheet.

Always loads the report skill. The answer comes in the skill's layout.

- match: {channel: slack, chat: "C000000CCCC"}
  agent:
    skills: {required: [expense-report]}
OperationsApproval, by one person
  1. David

    @Belle run the March expenses report.

  2. Belle

    Commands need approval in this channel. Run the report?

    ApproveReject

  3. Bob

    Only Bob can see this

    Bob presses Approve. Belle: You are not permitted to answer this request.

  4. Belle

    Approved by Alice. March expenses come to 31,870 euros.

Asks before running a command. Only Alice may approve.

- match: {channel: slack, chat: "C000000DDDD"}
  permissions:
    tools: {bash: ask}
  clicks:
    approve: {user: ["U000000AAAA"]}

One request, four outcomes: one sentence, a refusal, a formatted report, and a question that only Alice may answer. The skill is the harness's own, so its name depends on the harness you run.

A rule can also pin a model, attach a subagent or an expert, and start a turn on a pin or a new member. Rules for instructions and triggers can apply to one person or one role.

12 Your harness's catalog

Reach into your harness from the chat

Skills, subagents, experts and models are the harness's own, so what is there depends on the harness you run. Belle brings them into the chat, under the team's rules.

EngineeringDavid's screen
  1. David

    Only you can see this

    /belle skills use pr-tracker this week

    Belle, with the skill loaded for this one request: 3 pull requests changed since the last report. 2 are merged and 1 is waiting for review.

A skill called by name, for one request.

See more controls: subagents, experts and models
Purchasing6 people
  1. Alice

    @Belle compare the three vendor quotes and check each contract's notice period.

  2. Belle

    Finished

    Subagent exploredone

    Subagent generaldone

  3. Bob

    @Belle when does the current contract end?

    working
  4. Belle

    @Alice Quote B is the lowest. Its contract also has the longest notice period, 90 days.

ResearchIts own expert
  1. Charlie

    Only you can see this

    /belle experts list

    Installed: research-expert. A rule for this conversation selects research-expert.

DesignEve's screen
  1. Eve

    Only you can see this

    /belle models list

    Models: fast, careful.

    /belle models use careful

    New requests in this conversation use careful. A rule set for the conversation takes priority.

Watch subagents work, with Stop in reach. See which expert a conversation uses. Choose the model for a conversation.

Belle is cooking

More features on the stove.

Docs

Docs under construction

Under the hood

How Belle is put together, part by part.

The engine bay

Belle in layers: platform events pass through the coordinator and harness. Replies and actions return through the same layers.

  1. Platforms

    Where the team talks. One Belle serves several at once.

  2. Belle's coordinator

    Routes events, applies policy, schedules work, and directs the harness.

  3. The coupling

    What Belle hands the harness.

    1. 1Tool server Belle's tools, for the harness
    2. 2Skills chosen room by room
    3. 3Second Brain what the team shared
    4. 4One YAML file everything Belle owns
  4. The harness

    Runs the model and keeps the sessions. A Belle runs one at a time.

  5. The models

    Chat models in the harness, task models in Belle. Yours, from your providers or self-hosted.

Terminal User Interface

A light terminal app for admins, not for chat: see what Belle is doing, and step in when needed.

Belle ● CONNECTED|running 3queued 3|

Set it up (another site)

Feature matrix

Belle lives in a chat platform, the app where your team talks, such as Slack. Behind it runs a harness, the engine that drives the AI model and its tools. What Belle can do depends on both. Opt-in means an administrator turns the feature on.

Chat platforms

FeatureSlackMattermost (experimental)Matrix (experimental)Discord (experimental)
Talking to Belle
Direct messagesYesYesYesYes
MentionsYesYesYesYes
Replies in its threadsYesYesYesYes
Joins in without a mentionOpt-inOpt-inOpt-inOpt-in
Reply shows as it is writtenOpt-inOpt-inOpt-inOpt-in
Shows that it is workingYesYesYesYes
Progress cardYesYesYesYes
Emoji marks on messagesYesYesYesYes
Replies only you can seeYesYesNoTo a command or a click
CommandsYesYesYesYes
Questions and approvals
Asks you a questionButtons and textButtonsPollButtons and text
Asks you to approve an actionButtonsButtonsPollButtons
Stopping
Stop Belle mid-answerStop buttonStop buttonStop reactionStop button
Files
Reads files you shareYesYesYesYes
Sends you filesOpt-inYesYesYes
Tools
Reads the conversation historyYesYesYesYes
Searches messagesOpt-inYesYesYes
Pins messagesYesYesYesYes
Second BrainYesYesYesOpt-in
Extras
Encrypted roomsNoNoYesNo
Several accounts or workspacesYesYesYesYes
Home tabYesNoNoNo
Canvases, lists and bookmarksYesNoNoNo
Charts in repliesYesNoNoNo

On Matrix, commands start with !belle. On Mattermost and Matrix, Belle asks only questions with set choices, and search skips encrypted rooms and channels Belle is not in. On Discord, joining in without a mention and search need Discord's Message Content intent, and Second Brain reads only the channels you name.

Harnesses

FeatureJiuwenSwarmOpenCode v2 (experimental)Docker Agent (experimental)ACP (experimental)
Chat platforms
Works withSlack, Mattermost, MatrixSlack, Mattermost, Matrix, DiscordSlack, Mattermost, Matrix, DiscordSlack, Mattermost, Matrix, Discord
Questions and approvals
Asks you a questionYesYesNoNo
Asks you to approve an actionYesYesYesHarness actions
Stopping
Stop Belle mid-answerYesYesYesYes
Add a message to a running answerSlack onlyNoYesNo
Tools
Choose the AI modelYesYesYesNo
Limit tools per conversationNoYesYesNo
Limit skills per conversationYesYesPartialNo
Helper agentsYesNoPartialNo
Expert agentsYesNoYesNo
Extras
Scheduled jobsSlack onlyYesYesNot tested
Second BrainYesYesYesNot tested

Partial: Belle blocks what is not allowed, but the AI still sees it listed. On JiuwenSwarm, Second Brain does not learn from Mattermost. ACP drives any harness that speaks ACP v1, as a trial: what it gives depends on that harness, and Belle cannot narrow its tools, skills or model per conversation. Harness actions: Belle asks you before the harness runs one of its own actions.

Full details for operators (another site)