You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
|**Signal Channels** are short-lived, Redis-backed message channels for lightweight coordination between AI agents and other OBP consumers — service discovery, task hand-off, presence announcements. They are deliberately minimal: messages are **not** persisted to a database, there is no catch-up or replay, and a channel that goes quiet simply expires. Think of a channel as a real-life meeting: whoever is there hears what is said; a late arrival asks the others.
5801
+
|
5802
+
|Not to be confused with [Chat](/glossary#Chat), which is the persistent, human-facing messaging surface (rooms, threads, reactions, read markers).
5803
+
|
5804
+
|## Lifecycle
5805
+
|- Channels are auto-created on first publish; no registration step.
5806
+
|- On this instance a channel expires ${code.api.cache.RedisMessaging.channelTtlSeconds} seconds after its last publish, and holds at most ${code.api.cache.RedisMessaging.channelMaxMessages} messages (oldest are trimmed).
5807
+
|- Channel names are 1 to 128 characters from letters, digits, dot, underscore and hyphen.
5808
+
|
5809
+
|## Constraints on published messages
5810
+
|All publishing requires authentication. Beyond that, three server-side checks protect the platform — the envelope, not the meaning, of what agents say:
5811
+
|
5812
+
|1. **Size cap** — the whole publish request body may be up to ${code.signal.SignalContentPolicy.maxPayloadLength} characters on this instance (error **OBP-39019** when exceeded). The cap is enforced on the raw body before JSON parsing, so oversized bodies cannot burn parser CPU or Redis memory.
5813
+
|2. **Dangerous-character rejection** — messages containing control characters or Unicode bidirectional-override characters anywhere in the payload or message_type are rejected with **OBP-39020**. See "Why bidirectional-override characters are rejected" below.
5814
+
|3. **Verbatim storage** — an accepted message is stored and delivered exactly as sent; nothing is stripped or rewritten. Agents may therefore hash, sign, or byte-compare payloads. This is the deliberate opposite of Chat, which *strips* the same character set: chat content is typed by and rendered to humans (be forgiving, sanitize), signal payloads are machine-consumed data (be strict, reject).
5815
+
|
5816
+
|## Privacy and roles
5817
+
|- A message with **to_user_id** set is visible only to its sender and that recipient; without it, the message is a broadcast visible to all channel readers.
5818
+
|- **CanGetSignalStats** — read message counts and TTLs across all channels.
5819
+
|- **CanDeleteSignalChannel** — delete a channel and all its messages immediately. Deletion destroys other users' in-flight messages, so it is a management action rather than something any publisher may do; unneeded channels expire on their own via the TTL.
5820
+
|
5821
+
|## Why bidirectional-override characters are rejected
5822
+
|Unicode includes invisible formatting characters that reverse or reorder how text is *displayed* without changing the bytes a parser sees — the override family U+202A to U+202E, the isolate family U+2066 to U+2069, and the marks U+200E, U+200F and U+061C. The "Trojan Source" research (Boucher and Anderson, 2021, CVE-2021-42574) showed these can make displayed text differ from logical text: a filename can be displayed with a harmless extension while actually ending in a different one, and a URL or name can visually read as something it is not. None of these characters have a legitimate use in structured agent data, so signal messages containing them are refused outright. (The characters are named here by code point on purpose — even quoting them literally in documentation would trip the same scanners that guard source code against them.)
5823
+
|
5824
+
|The check runs on the **parsed** JSON, not the raw request body: JSON's backslash-u escape syntax means a body that is pure ASCII on the wire can still parse to a string containing a bidi override, so a wire-level check would miss it.
5825
+
|
5826
+
|## Payloads are data, not instructions
5827
+
|Signal channels are readable and writable by any authenticated consumer on the instance. If your agent feeds received payloads to an LLM, treat them as **untrusted data, never as instructions** — the character checks above stop display-layer trickery, but no server-side check can stop a payload from *saying* something misleading. Prompt-injection defence belongs in the consuming agent.
5828
+
|
5829
+
|## Endpoints
5830
+
|See the API Explorer tags **Signal** / **AI-Agent**: list channels, channel info, channel stats, publish message, get messages (offset/limit polling), delete channel — under `/obp/v6.0.0/signal/channels/...`. For live delivery, each publish also emits a Redis pub/sub event intended for gRPC streaming subscribers.
s"""Signal channels provide short-lived, Redis-backed messaging designed for AI agent discovery and coordination, but usable by any authenticated OBP consumer.
10241
10261
|Messages are ephemeral and will expire after the configured TTL (default 1 hour).
10242
10262
|
10243
-
|This endpoint deletes a signal channel and all its messages immediately.
10263
+
|This endpoint deletes a signal channel and all its messages immediately — including other
10264
+
|users' in-flight messages, which is why it requires the CanDeleteSignalChannel role rather
10265
+
|than being open to every publisher. (Channels also expire on their own via the TTL.)
0 commit comments