fix: agent can't see Gitea webhooks in Mattermost (bot-to-bot limitation)
All checks were successful
check / check (push) Successful in 11s
All checks were successful
check / check (push) Successful in 11s
Mattermost hides bot messages from other bots to prevent loops. Document why the notification poller exists as a workaround.
This commit is contained in:
parent
a6cd3e5997
commit
4f68638a28
@ -226,13 +226,26 @@ Docker build, and branch protection enforces CI. No single point of failure.
|
||||
Every repo has a Gitea webhook that sends all activity (pushes, PRs, issues,
|
||||
comments, reviews, CI status) to a channel in our self-hosted
|
||||
[Mattermost](https://mattermost.com) instance. This creates a real-time feed
|
||||
where everyone — human and agent — can see what's happening across all projects
|
||||
without cross-communication overhead.
|
||||
where the human can see what's happening across all projects without checking
|
||||
Gitea's notification inbox.
|
||||
|
||||
The agent also has its own Mattermost bot user (`@claw`), separate from the
|
||||
human. This means:
|
||||
**Important caveat:** The agent can't see this feed directly. Gitea's webhook
|
||||
messages arrive in Mattermost as a "bot" integration user. Mattermost
|
||||
deliberately hides bot messages from other bot users to prevent infinite
|
||||
bot-to-bot loops. This means the agent's Mattermost bot account is blind to the
|
||||
Gitea webhook feed, even though it's posted in a channel the agent has access
|
||||
to.
|
||||
|
||||
- The agent posts status updates to dedicated channels (`#git` for Gitea work,
|
||||
This is why we built the [notification poller](#the-notification-poller) — a
|
||||
separate Python script that polls Gitea's notification API directly, bypassing
|
||||
Mattermost entirely. The human sees Gitea activity via the Mattermost webhook
|
||||
feed; the agent sees it via the API poller. Same events, different delivery
|
||||
paths, because of a Mattermost platform limitation.
|
||||
|
||||
The agent has its own Mattermost bot user (`@claw`), separate from the human.
|
||||
This means:
|
||||
|
||||
- The agent posts status updates to dedicated channels (`#git` for work status,
|
||||
`#claw` for general work narration)
|
||||
- The human's DMs stay clean — only direct alerts and responses
|
||||
- In group channels, it's clear who said what
|
||||
@ -243,16 +256,33 @@ human. This means:
|
||||
A practical setup:
|
||||
|
||||
- **#git** — Real-time Gitea webhook feed (all repos) + agent's work status
|
||||
updates. Everyone sees commits, PRs, reviews, CI results as they happen.
|
||||
updates. The human sees commits, PRs, reviews, CI results as they happen. (The
|
||||
agent posts here but can't read the webhook messages — see caveat above.)
|
||||
- **#claw** — Agent's internal work narration. Useful for debugging what the
|
||||
agent is doing, but notifications muted so it doesn't disturb anyone.
|
||||
- **DM with agent** — Private conversation, sitreps, sensitive commands
|
||||
- **Project-specific channels** — For coordination with external collaborators
|
||||
|
||||
The webhook feed in #git means nobody needs to check Gitea's notification inbox
|
||||
manually. PRs, reviews, and CI results flow into a channel that's always open.
|
||||
The agent monitors the same feed (via its notification poller) and can react to
|
||||
events in near-realtime.
|
||||
### The Notification Poller
|
||||
|
||||
Because the agent can't see Gitea webhooks in Mattermost (bot-to-bot visibility
|
||||
issue), we built a lightweight Python script that polls the Gitea notifications
|
||||
API every 2 seconds and wakes the agent via OpenClaw's `/hooks/wake` endpoint
|
||||
when new notifications arrive.
|
||||
|
||||
Key design decisions:
|
||||
|
||||
- **The poller never marks notifications as read.** That's the agent's job after
|
||||
processing. Prevents the poller and agent from racing.
|
||||
- **Tracks notification IDs, not counts.** Only fires on genuinely new
|
||||
notifications, not re-reads of existing ones.
|
||||
- **The wake message tells the agent to route output to Gitea/Mattermost, not
|
||||
DM.** Prevents chatty notification processing from disturbing the human.
|
||||
- **Zero dependencies.** Python stdlib only (`urllib`, `json`, `time`). Runs
|
||||
anywhere.
|
||||
|
||||
Full source code is available in
|
||||
[OPENCLAW_TRICKS.md](OPENCLAW_TRICKS.md#the-gitea-notification-poller).
|
||||
|
||||
## CI: Gitea Actions
|
||||
|
||||
|
||||
Loading…
Reference in New Issue
Block a user