Channels

Connect OpenSentinel to any messaging platform. Each channel runs independently — enable only what you need.

Zero-config channels. Every channel is opt-in. Set its environment variable and OpenSentinel will start listening automatically. No channel? No problem — unconfigured services are silently skipped at startup.

Overview

OpenSentinel supports 10+ input channels. Each channel is activated by setting the corresponding environment variable in your .env file. All channels run in parallel on a single instance and share the same brain, memory, and tool system.

ChannelEnv VariableProtocolStatus
TelegramTELEGRAM_BOT_TOKENBot API (grammY)Stable
DiscordDISCORD_BOT_TOKENGateway (discord.js)Stable
SlackSLACK_BOT_TOKENBolt / Socket ModeStable
WhatsAppWHATSAPP_ENABLEDBaileys (Web)Stable
SignalSIGNAL_ENABLEDsignal-cli JSON-RPCStable
iMessageIMESSAGE_ENABLEDBlueBubbles / AppleScriptmacOS only
WebSocketAlways onws:// (Bun native)Stable
Web DashboardAlways onHTTP + ReactStable
REST APIAlways onHTTP (Hono)Stable
VoiceVOICE_ENABLEDMicrophone + STTLinux
💡
Multiple channels at once. You can enable Telegram, Discord, Slack, and every other channel simultaneously. Each maintains its own session history per user, but they all share the same Claude-powered brain and tool execution engine.

Telegram

Telegram is the primary and most feature-rich channel for OpenSentinel. It uses the grammY framework and supports text messages, voice notes with automatic transcription, inline keyboards, and full tool execution.

Setup

Create a bot with BotFather

Open Telegram, search for @BotFather, and send /newbot. Follow the prompts to choose a name and username. BotFather will give you a bot token.

Configure your environment
.env
TELEGRAM_BOT_TOKEN=your-telegram-bot-token
TELEGRAM_CHAT_ID=your-chat-id  # Your personal chat ID (restricts access)
Start OpenSentinel

The Telegram bot starts automatically when TELEGRAM_BOT_TOKEN is set. Find your bot in Telegram and send /start.

ℹ️
Access control. Set TELEGRAM_CHAT_ID to restrict the bot to your personal chat. Any message from a different chat ID is silently ignored. To find your chat ID, send a message to the bot and check the server logs.

Features

  • Text messages — Full conversational AI with Claude, including tool execution (shell, web search, file operations, etc.)
  • Voice messages — Automatic STT transcription via OpenAI Whisper, processes the transcription as a text query, and optionally replies with TTS audio via ElevenLabs
  • Markdown formatting — Responses are sent with Telegram Markdown, with automatic plaintext fallback on parse errors
  • Long message splitting — Messages exceeding Telegram's 4096-character limit are automatically split at natural break points
  • Session history — Last 20 messages per user are maintained for multi-turn conversations
  • Tool usage display — Shows which tools were used (e.g., "Used: shell, web_search") above the response

Commands

CommandDescription
/startWelcome message with capabilities overview
/helpShow all available commands and usage examples
/clearClear conversation history for the current session
/remind <time> <message>Set a reminder (e.g., /remind 5m Check the oven). Supports s, m, h units
/mode <name>Switch personality mode (e.g., concise, creative, technical)
/expert <domain>Activate a domain expert persona (e.g., /expert python)

How it works

src/inputs/telegram/bot.ts
import { Bot, session } from "grammy";
import { handleMessage, handleVoice } from "./handlers";

const bot = new Bot(env.TELEGRAM_BOT_TOKEN);

// Session middleware maintains per-user conversation history
bot.use(session({ initial: () => ({ messages: [] }) }));

// Restrict to your personal chat
bot.use(async (ctx, next) => {
  if (ctx.chat?.id?.toString() !== env.TELEGRAM_CHAT_ID) return;
  await next();
});

// Route text and voice messages to handlers
bot.on("message:text", handleMessage);
bot.on("message:voice", handleVoice);

Voice messages are downloaded, transcribed with Whisper, and processed as text. If the response is short enough (under 1000 characters), a voice reply is also generated via ElevenLabs TTS and sent back as an .ogg file.

Discord

The Discord channel uses discord.js and supports slash commands, direct messages, server mentions, and voice channel operations. Per-user sessions are maintained with the last 20 messages of context.

Setup

Create a Discord application

Go to discord.com/developers/applications, click New Application, then navigate to Bot and click Reset Token to get your bot token.

Enable Privileged Gateway Intents

In the Bot settings, enable all three Privileged Gateway Intents:

  • Presence Intent
  • Server Members Intent
  • Message Content Intent
Configure your environment
.env
DISCORD_BOT_TOKEN=your-discord-bot-token
DISCORD_CLIENT_ID=your-client-id
DISCORD_GUILD_ID=your-server-id         # Your server ID
DISCORD_ALLOWED_USER_IDS=your-user-id  # Comma-separated
Invite the bot to your server

Use the OAuth2 URL generator in the developer portal. Select bot and applications.commands scopes, then grant Send Messages, Read Message History, Use Slash Commands, and Connect (for voice) permissions.

⚠️
Privileged Intents are required. If you skip enabling Privileged Gateway Intents, OpenSentinel will fail to connect and log a detailed error message with instructions. The bot will still start but Discord will be unavailable.

Slash Commands

CommandDescription
/ask <question>Ask a single question with full tool execution
/chat <message>Continue a multi-turn conversation with context
/clearClear your conversation history (ephemeral reply)
/remind <time> <unit> <message>Set a reminder with dropdown unit selection (seconds, minutes, hours)
/statusCheck bot status and your session message count
/helpShow all available commands and tips
/voice joinJoin your current voice channel
/voice leaveLeave the voice channel
/voice speak <text>Speak text aloud in the voice channel via TTS

Features

  • Slash commands — All commands are registered as Discord slash commands with proper descriptions and option types
  • DM support — Message the bot directly for private conversations
  • Deferred replies — Long-running tool executions use Discord's deferred reply system so the interaction never times out
  • Message splitting — Responses exceeding Discord's 2000-character limit are automatically split into follow-up messages
  • User restriction — Set DISCORD_ALLOWED_USER_IDS to restrict access to specific Discord users
  • Voice channels — Join voice, speak with TTS, and leave via slash commands

Slack

The Slack channel uses Bolt for JavaScript and supports both HTTP receiver mode and Socket Mode for deployments behind firewalls. It handles app mentions, DMs, file sharing, threaded conversations, and slash commands.

Setup

Create a Slack app

Go to api.slack.com/apps and click Create New App. Choose From scratch, name it "OpenSentinel", and select your workspace.

Configure bot permissions

Under OAuth & Permissions, add these Bot Token Scopes: app_mentions:read, chat:write, commands, files:read, im:history, im:read, im:write, reactions:read, reactions:write, users:read.

Install to workspace and configure
.env
SLACK_BOT_TOKEN=xoxb-your-bot-token
SLACK_SIGNING_SECRET=your-signing-secret
SLACK_APP_TOKEN=xapp-your-app-token     # For Socket Mode
SLACK_SOCKET_MODE=true                   # Use Socket Mode (recommended)

Slash Commands

CommandDescription
/opensentinel ask <question>Ask a single question
/opensentinel chat <message>Continue a multi-turn conversation
/opensentinel clearClear your conversation history
/opensentinel remind <time> <message>Set a reminder (e.g., /opensentinel remind 5m Stand up)
/opensentinel statusCheck bot status and capabilities
/opensentinel helpShow all available commands

Individual slash commands are also available: /opensentinel-ask, /opensentinel-chat, /opensentinel-clear, /opensentinel-remind, /opensentinel-status, /opensentinel-help.

Features

  • App mentions — @mention the bot in any channel to ask a question; replies are threaded
  • Direct messages — Chat privately with the bot in DMs
  • Threaded conversations — Thread-aware session tracking preserves context across a full thread
  • File handling — Shared audio files are automatically transcribed
  • Processing indicators — An hourglass reaction is added while processing and removed on completion
  • Socket Mode — No public URL needed; works behind firewalls and NAT
  • User/channel restrictions — Set SLACK_ALLOWED_USER_IDS or SLACK_ALLOWED_CHANNEL_IDS to control access

WhatsApp

The WhatsApp channel uses the Baileys library to connect to WhatsApp Web. It authenticates via QR code scan, supports multi-device mode, and persists authentication state across restarts.

Setup

Enable WhatsApp and start
.env
WHATSAPP_ENABLED=true
WHATSAPP_AUTH_DIR=./whatsapp-auth          # Credential storage path
WHATSAPP_ALLOWED_NUMBERS=+1234567890     # Comma-separated allowed numbers
Scan the QR code

On first launch, a QR code is printed to the terminal. Open WhatsApp on your phone, go to Linked Devices, and scan it. Authentication persists in the whatsapp-auth directory, so you only need to scan once.

Features

  • Text messages — Full AI conversations with tool execution
  • Typing indicators — Shows "composing" while processing, then "paused" when done
  • Auto-reconnect — Automatically reconnects on disconnect (unless logged out)
  • Number allowlist — Set WHATSAPP_ALLOWED_NUMBERS to restrict access
  • Per-conversation context — Last 10 messages are maintained per contact
💡
Persistent auth. After the first QR scan, credentials are stored in the whatsapp-auth directory. Subsequent restarts reconnect automatically without rescanning.

Signal

The Signal channel uses signal-cli in JSON-RPC mode to send and receive encrypted messages. All messages remain end-to-end encrypted through Signal's protocol.

Setup

Install and link signal-cli
Terminal
# Install signal-cli (Linux)
$ wget https://github.com/AsamK/signal-cli/releases/latest/download/signal-cli-0.13.2-Linux.tar.gz
$ tar xf signal-cli-*.tar.gz -C /opt/
$ ln -s /opt/signal-cli-*/bin/signal-cli /usr/local/bin/

# Link to your existing Signal account
$ signal-cli link -n "OpenSentinel"
Configure your environment
.env
SIGNAL_ENABLED=true
SIGNAL_PHONE_NUMBER=+1234567890
SIGNAL_CLI_PATH=signal-cli              # Path to binary (default: signal-cli)
SIGNAL_ALLOWED_NUMBERS=+1234567890    # Comma-separated allowed numbers

Features

  • End-to-end encryption — All messages use Signal's encryption protocol
  • JSON-RPC interface — OpenSentinel spawns signal-cli as a child process and communicates via JSON-RPC over stdin/stdout
  • Number allowlist — Restrict access to specific phone numbers
  • Per-contact context — Last 10 messages maintained per sender
Architecture
// Signal-cli runs as a subprocess in JSON-RPC mode
// OpenSentinel reads incoming messages from stdout
// and writes outgoing messages to stdin

signal-cli -u +1234567890 jsonRpc
  stdout → OpenSentinel (receives messages)
  stdin  ← OpenSentinel (sends replies)

iMessage

The iMessage channel supports two modes: BlueBubbles (requires a BlueBubbles server running on macOS) and AppleScript (direct macOS integration via the Messages app). Both modes provide full AI conversation capabilities.

Setup

# .env - BlueBubbles mode (any platform, Mac server required)
IMESSAGE_ENABLED=true
IMESSAGE_MODE=bluebubbles
IMESSAGE_BLUEBUBBLES_URL=http://192.168.1.100:1234
IMESSAGE_BLUEBUBBLES_PASSWORD=your-password
IMESSAGE_ALLOWED_NUMBERS=+1234567890

Features

  • BlueBubbles mode — Connects to a BlueBubbles server via REST API. Run OpenSentinel on any platform while the Mac server handles iMessage
  • AppleScript mode — Direct integration with the Messages app on macOS. Requires Full Disk Access permission for the terminal/process
  • Polling — Both modes use configurable polling intervals (default: 5 seconds) to check for new messages
  • Number restriction — Set IMESSAGE_ALLOWED_NUMBERS to control who can interact with the bot
ℹ️
macOS required. AppleScript mode only works on macOS. BlueBubbles mode lets you run OpenSentinel on Linux while a Mac Mini or similar device handles the iMessage bridge via BlueBubbles.

WebSocket

The WebSocket channel provides real-time, bidirectional communication for custom integrations. It is always available at ws://localhost:8030/ws and uses Bun's native WebSocket implementation for high performance.

Message Protocol

The WebSocket interface uses a JSON-based message protocol. Clients send typed messages and receive streamed responses including text chunks, tool execution events, and completion signals.

Client → Server
// Send a message with tool execution
{
  "type": "chat_with_tools",
  "id": "msg-123",
  "payload": {
    "messages": [
      { "role": "user", "content": "What files are in my Downloads?" }
    ],
    "userId": "user-1"
  }
}
Server → Client (streamed)
// Text chunks arrive in real-time
{ "type": "chunk", "id": "msg-123", "payload": { "text": "Let me check " } }
{ "type": "tool_start", "id": "msg-123", "payload": { "toolName": "shell" } }
{ "type": "tool_result", "id": "msg-123", "payload": { "toolName": "shell", "toolResult": "..." } }
{ "type": "complete", "id": "msg-123", "payload": { "content": "..." } }

Supported Message Types

Client MessageDescription
chatSimple chat without tool execution, streamed response
chat_with_toolsFull chat with tool execution, streams chunks + tool events
pingKeepalive ping; server responds with pong
cancelCancel an in-flight request by message ID

Features

  • Streaming responses — Text arrives token-by-token in real-time
  • Tool execution events — Observe tool_start and tool_result events as they happen
  • Request cancellation — Cancel long-running requests mid-stream
  • Connection tracking — Each connection gets a unique ID and activity timestamp
  • Broadcast support — Server can broadcast messages to all connected clients

Web Dashboard

OpenSentinel includes a built-in React web dashboard accessible at http://localhost:8030. It provides five views: Chat, Memories, Graph, Email, and Settings. The dashboard is always available when the server is running.

Features

  • Chat interface — Full-featured chat UI with markdown rendering, code highlighting, and file attachments
  • Memory explorer — Browse and search the RAG vector memory system
  • OSINT Graph Explorer — Interactive D3 visualization of entity relationships and knowledge graph
  • Web email client — Browse inbox, read HTML emails, download/view attachments, compose with attachments, reply, and forward
  • Settings panel — Configure personality, active tools, and channel preferences
  • Real-time streaming — Uses the WebSocket channel under the hood for token-by-token streaming
  • Mobile responsive — Works on phones and tablets

Building the Dashboard

The dashboard is pre-built in production. For development:

Terminal
$ cd src/web && bun install && bun run build

REST API

The REST API is built on Hono and provides full programmatic access to OpenSentinel. It is always available at http://localhost:8030 alongside the web dashboard.

Primary Endpoint

Terminal
$ curl -X POST http://localhost:8030/api/ask \
    -H "Content-Type: application/json" \
    -d '{"message": "What is the weather in NYC?"}'

Response Format

JSON Response
{
  "content": "The current weather in New York City is...",
  "inputTokens": 1250,
  "outputTokens": 340,
  "toolsUsed": ["web_search"]
}

Multi-turn Conversations

Pass a message array for multi-turn conversations:

Terminal
$ curl -X POST http://localhost:8030/api/ask \
    -H "Content-Type: application/json" \
    -d '{
      "messages": [
        {"role": "user", "content": "Remember that my name is Alex"},
        {"role": "assistant", "content": "Got it! I will remember that your name is Alex."},
        {"role": "user", "content": "What is my name?"}
      ]
    }'

Features

  • Full tool execution — The API has access to all tools (shell, search, files, etc.)
  • Conversation context — Pass full message arrays for multi-turn dialogue
  • Token usage — Every response includes input and output token counts
  • Tool reporting — The toolsUsed field lists all tools invoked during the response
💡
Pair with WebSocket for streaming. The REST API returns the full response at once. If you need token-by-token streaming, use the WebSocket channel instead. The web dashboard uses WebSocket for its streaming chat UI.

Voice

The Voice channel enables hands-free interaction with OpenSentinel through wake word detection, voice activity detection (VAD), and continuous conversation mode. It uses local audio capture with arecord (Linux) and processes speech through OpenAI Whisper for transcription.

Setup

.env
VOICE_ENABLED=true
OPENAI_API_KEY=sk-proj-...             # Required for Whisper STT
ELEVENLABS_API_KEY=your-elevenlabs-key      # Optional, for TTS responses

Wake Word Detection

Say "Hey OpenSentinel" to activate the assistant. The detector uses a hybrid approach combining local MFCC-based keyword spotting with cloud-based STT for high accuracy and low latency.

FeatureDetails
Default wake wordhey opensentinel
Accepted variationshey open sentinel, hey opensentinal, hey open sentimental, and more
MatchingLevenshtein distance + phonetic encoding for fuzzy matching
Confidence threshold0.6 minimum (configurable)
Detection timeout5 seconds of inactivity returns to sleep

Processing Pipeline

Pipeline
Microphone → 16kHz PCM → VAD (speech detection)
  → MFCC local spotting (pre-filter)
  → Whisper STT (transcription)
  → Wake word matching (fuzzy + phonetic)
  → Command extraction
  → Claude AI (processing)
  → ElevenLabs TTS (voice reply)

Features

  • Wake word detection — Hybrid MFCC + STT approach filters audio locally before sending to cloud, reducing API calls
  • Voice Activity Detection — Detects speech start/end to segment audio accurately. Configured for -35 dB silence threshold with 200ms minimum speech duration
  • Continuous conversation — After wake word activation, the assistant stays awake for 5 seconds of inactivity, allowing natural multi-turn voice conversations
  • Command extraction — Text after the wake word is automatically extracted as a command (e.g., "Hey OpenSentinel, what time is it?" extracts "what time is it?")
  • Customizable wake word — Change the wake word at runtime. New phonetic variations are added automatically
  • TTS responses — Replies under 1000 characters are automatically spoken aloud via ElevenLabs
⚠️
Linux only. Voice input currently requires arecord (ALSA utils) which is available on Linux. macOS and Windows support is planned for a future release.