[BUG] Telegram MCP plugin: inbound notifications/claude/channel never delivered to session (outbound works)

Resolved 💬 20 comments Opened Mar 20, 2026 by jmercado1986 Closed Jun 25, 2026
💡 Likely answer: A maintainer (localden, collaborator) responded on this thread — see the highlighted reply below.

Preflight Checklist

  • [x] I have searched existing issues and this hasn't been reported yet
  • [x] This is a single bug report (please file separate reports for different bugs)
  • [x] I am using the latest version of Claude Code

What's Wrong?

Environment:

  • macOS Darwin 25.4.0
  • Claude Code (Opus 4.6, 1M context)
  • Telegram plugin v0.0.1 (~/.claude/plugins/cache/claude-plugins-official/telegram/0.0.1)
  • Runtime: Bun

What happens:

  1. User sends a DM to the bot from Telegram
  2. Bot receives the message — sendChatAction('typing') fires, visible in Telegram as "typing..."
  3. gate() returns deliver (user ID 767**** is in access.json allowlist)
  4. mcp.notification({ method: 'notifications/claude/channel', params: {...} }) is called (server.ts line 578)
  5. Notification never arrives in the Claude Code session — no <channel> tag appears in the conversation

What works:

  • Outbound reply tool works perfectly — mcp__plugin_telegram_telegram__reply sends messages to Telegram successfully (confirmed: message ID 26 delivered)
  • Bot token is valid, bot is polling (ps aux shows bun process running)
  • Access config is correct (dmPolicy: "allowlist", user ID in allowFrom)

What was tried:

  • Restarting Claude Code sessions (multiple times)
  • Reconfiguring via /telegram:configure
  • Verifying access.json is correct
  • Confirming MCP server process is running (PID visible in ps aux)

Diagnosis:
The MCP stdio transport between the Telegram server and Claude Code is functional for tool calls (request/response pattern) but mcp.notification() (server-initiated push) is silently
dropped or not processed by Claude Code's MCP client. The void fire-and-forget on line 578 of server.ts means any notification delivery failure is swallowed without logging.

Relevant files:

  • ~/.claude/plugins/cache/claude-plugins-official/telegram/0.0.1/server.ts — line 578: void mcp.notification(...)
  • ~/.claude/channels/telegram/access.json — allowlist config
  • ~/.claude/channels/telegram/.env — bot token

What Should Happen?

Expected behavior: Inbound Telegram messages should appear in the Claude Code conversation as <channel source="telegram" ...> events, allowing Claude to read and respond.

Error Messages/Logs

{"debug":"Starting connection with timeout of 30000ms","timestamp":"2026-03-19T23:47:32.549Z"}                                                                                            
  {"debug":"Successfully connected to undefined server in 228ms","timestamp":"2026-03-19T23:47:32.776Z"}
  {"debug":"Connection established with capabilities: {\"hasTools\":true,\"hasPrompts\":false,\"hasResources\":false,\"hasResourceSubscribe\":false,\"serverVersion\":{\"name\":\"telegram\"
  ,\"version\":\"1.0.0\"}}","timestamp":"2026-03-19T23:47:32.776Z"}                                                                                                                         
  {"debug":"Channel notifications skipped: server plugin:telegram:telegram not in --channels list for this session","timestamp":"2026-03-19T23:47:32.780Z"}                                 
  {"debug":"Channel notifications skipped: server plugin:telegram:telegram not in --channels list for this session","timestamp":"2026-03-19T23:47:32.780Z"}                                 
  {"debug":"Calling MCP tool: reply","timestamp":"2026-03-19T23:50:05.506Z"}
  {"debug":"Tool 'reply' completed successfully in 332ms","timestamp":"2026-03-19T23:50:05.838Z"}                                                                                           
                                                    
  And from a previous session where it did work (2026-03-19T23-33-20-145Z.jsonl):                                                                                                           
                                                    
  {"debug":"Channel notifications registered","timestamp":"2026-03-19T23:33:21.324Z"}                                                                                                       
  {"debug":"notifications/claude/channel: yo!","timestamp":"2026-03-19T23:35:03.717Z"}                                                                                                      
  {"debug":"Tool 'reply' completed successfully in 401ms","timestamp":"2026-03-19T23:35:18.476Z"}

Steps to Reproduce

Steps to reproduce:

  1. Install the Telegram plugin (plugin:telegram:telegram)
  2. Configure bot token in ~/.claude/channels/telegram/.env
  3. Add a user to the allowlist in ~/.claude/channels/telegram/access.json
  4. Start a Claude Code session — send a Telegram message to the bot
  5. Sometimes it works (Channel notifications registered), sometimes it doesn't (Channel notifications skipped: server plugin:telegram:telegram not in --channels list for this session)
  6. Restart Claude Code and repeat — the result is non-deterministic

Expected: Channel notifications registered on every session start
Actual: Intermittent — some sessions register, others skip with not in --channels list

How to verify the state: Check the latest .jsonl file in:
~/Library/Caches/claude-cli-nodejs/<project-path>/mcp-logs-plugin-telegram-telegram/

Line 4 will say either:

  • "Channel notifications registered" (working)
  • "Channel notifications skipped: server plugin:telegram:telegram not in --channels list for this session" (broken)

Workaround found: None. Restarting sessions sometimes fixes it, sometimes doesn't. The --channels flag that controls this appears to be set internally by Claude Code and is not
user-configurable.

Claude Model

Opus

Is this a regression?

I don't know

Last Working Version

_No response_

Claude Code Version

Claude Code v2.1.80

Platform

Anthropic API

Operating System

macOS

Terminal/Shell

Warp

Additional Information

_No response_

View original on GitHub ↗

20 Comments

biosed · 3 months ago

Same issue here.

  • OS: Fedora 43, Linux 6.18.15 aarch64 (Asahi Linux on Apple Silicon)
  • DE: KDE Plasma on Wayland
  • Claude Code: 2.1.80
  • Plugin: telegram@claude-plugins-official v0.0.1

Bot receives DMs, sends typing indicator, passes the gate (pairing/allowlist all working), and outbound reply tool works fine — but notifications/claude/channel never surfaces in the session. Reloading plugins and restarting the session didn't help.

werkhaus · 3 months ago

+1 — experiencing the exact same issue on macOS Darwin 25.3.0, Claude Code 2.1.81, Telegram plugin v0.0.1.

Confirmed via MCP logs:

{"debug":"Channel notifications skipped: server plugin:telegram:telegram not in --channels list for this session"}
  • Outbound reply tool works fine (messages delivered to Telegram)
  • Bot is polling and consuming updates (verified via getUpdates returning empty)
  • access.json is correctly configured (allowlist policy, user ID present)
  • Multiple session restarts + /reload-plugins did not resolve
  • Log file: ~/Library/Caches/claude-cli-nodejs/-Users-Zissou/mcp-logs-plugin-telegram-telegram/2026-03-20T23-02-46-128Z.jsonl

Would love to see a fix or a user-facing --channels flag to force registration.

git-bafshar · 3 months ago
st3fus · 3 months ago

Same here, MacBook Pro

cversek · 3 months ago

Ran into this same pattern - outbound replies work fine but inbound channel notifications never surface. A few things that fixed it:

  1. Stale marketplace cache. Run claude plugins marketplace update before anything else. The cache doesn't auto-refresh, so you might be running an older plugin version even after reinstalling.
  1. Orphan bun processes. If a previous session crashed, the old bun process can still be polling the Telegram bot token. Telegram only allows one poller per token (409 Conflict), so the new session's server connects but can't receive messages. Check with ps aux | grep "bun.*server" and kill any zombies.
  1. The --channels flag is required at launch. Having the server in .mcp.json loads the MCP tools (so outbound works), but it doesn't activate channel event delivery. You need:

``
claude --channels plugin:telegram@claude-plugins-official
``

  1. Feature flag check. Channels require tengu_harbor: true in your GrowthBook config:

``bash
cat ~/.claude.json | python3 -c "import json,sys; print(json.load(sys.stdin).get('cachedGrowthBookFeatures',{}).get('tengu_harbor'))"
`
Should print
True`.

I wrote up the full debugging process and permission relay setup here: https://github.com/cversek/cc-telegram-channel-tutorial

maysee4 · 3 months ago

Confirming this is the same issue on Claude Code 2.1.81 (macOS).

Symptoms:

  • Telegram plugin connects successfully
  • Bot receives messages and shows "typing"
  • Outbound/plugin tools work
  • Inbound messages never appear in the Claude session

Debug logs consistently show:
"Channel notifications skipped: server plugin:telegram:telegram not in --channels list for this session"

Important detail:

  • claude --help shows no usable --channels flag
  • claude update confirms I am already on the latest version (2.1.81)

From the user side, there appears to be no way to enable the required channel subscription, even though the Telegram plugin expects it.

This looks like a CLI/plugin mismatch rather than a configuration issue.

Happy to provide full debug logs if needed.

DarkCloudCZ · 3 months ago

Description:
Inbound Telegram messages are intermittently not delivered to the Claude Code session. The user must send the same message 2+ times for it to be received. Outbound replies (via the reply tool) work correctly every time. Sometimes it works on the first try and sometimes I have to send the message 4 times.

Behavior:

  • Telegram bot receives the message (visible in Telegram as "delivered")
  • Message is NOT surfaced in the Claude Code session
  • No error is shown to the user
  • Resending the same message usually works on the 2nd attempt

Environment:

  • OS: Linux (Ubuntu)
  • Claude Code with Telegram plugin via MCP
  • Long-running session (days)

Suspected cause:
Likely related to the zombie process / polling conflict described in the linked issues — when multiple processes compete for the Telegram polling slot, messages are randomly split between them and the active Claude session misses some.
Edit: I tried to kill all the processes and start them again. But nothing changed

Impact:
User loses confidence that messages are being received. Workaround is to send each message twice, which is not acceptable UX.

juanpablodlc · 3 months ago

Same bug here.... I can't get telegram to reliably work Claude team please fix

Pectics · 3 months ago

+1, I can reproduce what looks like the same channel allowlist/routing problem, but with a locally installed development plugin channel rather than Telegram.

In my case:

  • the plugin installs successfully from a local marketplace
  • the plugin MCP server connects successfully
  • tools/resources are available
  • Claude Code shows the development channel confirmation dialog
  • I explicitly confirm I am using this for local development

But channel registration still fails with:

MCP server "plugin:napcat:napcat": Channel notifications skipped: plugin napcat@local-napcat is not on the approved channels allowlist (use --dangerously-load-development-channels for local dev)

So the UI confirmation appears to be accepted, but the runtime still behaves as if the plugin channel is not allowlisted.

Filed separately here for the local-plugin repro: #43064

uditya-kumar · 3 months ago

I dug into this a bit and wanted to share a hypothesis that might help pinpoint the issue quickly.

Observed behavior

  • Telegram plugin receives the message successfully
  • "Typing" indicator is sent
  • MCP notification is dispatched
  • Notification is then skipped with:
server plugin:telegram:telegram not in --channels list for this session

Likely root cause

It looks like channel matching may be relying only on the plugin/server name segment extracted from values like:

plugin:telegram:telegram → "telegram"

and comparing that directly against the --channels entries.

This can fail when:

  • The plugin’s internal/manifest name differs from the identifier used in --channels
  • A more complete identifier (e.g. something like name@marketplace, which may already be available on the connection/config object) isn’t used during matching

In that case, even though the correct channel is configured, the lookup fails and the notification gets dropped at the gating stage.

Why this fits the symptoms

  • Outbound signals (like typing) still work because the connection exists
  • Inbound notifications are dropped only during channel gating
  • The log consistently shows a mismatch rather than a transport issue

Suggested direction

It may help to:

  1. Keep the current name-based match as the primary check
  2. If that fails, attempt a fallback match using the full plugin identifier (if available), rather than only the extracted name segment
  3. Ensure this matching logic is applied consistently across all call sites (gating + telemetry/logging), so behavior doesn’t diverge

Debugging improvement

The current error message doesn’t show what channels are actually registered, which makes this harder to diagnose.

Including that would make issues like this immediately obvious, e.g.:

server plugin:telegram:telegram not in --channels list (registered: <...>)

or:

(no channels registered)

This would help distinguish between:

  • name mismatch
  • empty/misconfigured session
  • parsing issues
git-bafshar · 3 months ago

Claude got it working! Posting what actually fixed it in case it helps.

What was happening

The bot was receiving messages fine (typing indicator visible in Telegram, outbound reply tool working), but inbound messages never surfaced in the session. MCP logs showed:

Channel notifications skipped: server plugin:telegram:telegram not in --channels list for this session

Two separate problems

1. Zombie bun process

A previous session's bun server was still running in the background (check with ps aux | grep "bun.*server"). Telegram delivers each update to exactly one active poller, so the zombie was consuming messages before the current session's process could see them. Kill it with kill -9 <PID> and verify only one bun process remains.

Hat tip to @cversek for calling this pattern out explicitly.

2. The --channels flag

Even after clearing the zombie, channel notifications were still skipped. The --channels flag has to be passed at session launch to tell the MCP client to route notifications/claude/channel events into the conversation. Without it, the server fires the notification but the client drops it regardless.

The working invocation:

claude --channels plugin:telegram@claude-plugins-official

Again, @cversek's comment named this directly — that was the unlock.

A note on running multiple sessions

If you run multiple Claude sessions simultaneously, each one spawns its own bun process polling the same bot token. Telegram splits updates across all active pollers, so messages land randomly across sessions. The pattern that works cleanly: one dedicated session launched with --channels, all others without. A shell function makes this easy:

claude-tg() { claude --channels plugin:telegram@claude-plugins-official "$@" }

Root cause note for Anthropic

@uditya-kumar's comment gave the clearest technical framing here: the --channels check fails because session-level channel registration never happens for GUI-launched sessions. The --channels flag is CLI-only with no settings.json equivalent, so Claude Desktop sessions never receive it and channel notifications are permanently skipped in that context.

The tengu_harbor feature flag being enabled and access.json being correctly configured are both necessary but not sufficient — the session-level registration is the missing piece. A fix that automatically registers channels when a plugin declares the experimental['claude/channel'] capability (which the telegram plugin already does in server.ts) would make this work without requiring users to discover and manually pass the flag.

quangthien27 · 3 months ago

Seems Claude Code session that loads the Telegram plugin spawns a bun poller but doesn't kill it on exit 🤔

khwoo8905-maker · 3 months ago

Same issue here — adding environment details.

Environment:

  • macOS Darwin 25.2.0 (Mac Mini M4 32GB)
  • Claude Code v2.1.101
  • Telegram plugin v0.0.5 (same behavior on v0.0.4)

Symptoms:

  • Bot polling works (Telegram shows "typing" indicator)
  • Outbound reply tool works fine
  • mcp.notification({ method: 'notifications/claude/channel', ... }) is called but never surfaces in the Claude Code session
  • No new message files written to ~/.claude/channels/telegram/messages/ since March 25
  • getUpdates from curl returns ok: true with empty result (no 409), suggesting the bot consumes updates but the notification is silently dropped
  • Killing the bot process and letting MCP restart does not resolve the issue

Tried:

  • Multiple /mcp reconnections
  • Bot process kill & restart
  • deleteWebhook + drop_pending_updates
  • Plugin upgrade from 0.0.4 → 0.0.5
  • Fresh Claude Code sessions

This has been persistent since late March 2026. Would appreciate any workaround or fix.

idvorkin-ai-tools · 3 months ago

Different approach: persistent poller outside the Claude session

The fixes above work but are fragile — messages that arrive during a Claude restart are still lost, because the bun poller dies with the session and the Bot API cursor has already advanced.

We split it into two processes:

telegram_bot.py — persistent Python, runs independently of Claude:

  • Owns getUpdates forever, writes every message to SQLite (WAL mode)
  • Singleton via flock — no zombie/split-update problem by construction
  • Survives Claude restarts, crashes, reconnects

server.ts (modified) — no longer polls Telegram:

  • Reads undelivered rows from SQLite, emits MCP notifications
  • On each Claude start, catches up on everything missed while Claude was down

--channels is still required for MCP routing, but accumulation happens regardless — restart with --channels and you get everything that arrived while Claude was down.

When things go wrong

We ship a telegram_debug.py --doctor that checks the whole chain in one pass: bot.py PID alive, Unix socket accepting, inbound.db row counts, server.ts process count, source/plugin hash drift. Common failure modes it catches:

  • Zombie bridge: two server.ts processes — doctor flags it, fix is kill <pids> then /reload-plugins
  • Plugin auto-update overwrites server.ts: doctor detects via sha256 drift, fix is cp redeploy
  • bot.py died: doctor shows missing PID, fix is nohup telegram_bot.py ... &
  • Stale bot.sock: handled automatically on bot.py startup via connect-then-unlink

Liveness signal: bot.py stamps 👀 on receive, server.ts stamps 🫡 on delivery. Both glyphs on a message = full pipeline ran.

Full design doc (SQLite WAL rationale, singleton semantics, 409 retry, the pkill-by-name trap we hit): harden-telegram/design.md

Farhankhan0128 · 2 months ago

Telegram plugin: inbound DMs never injected into conversation (outbound works)

  • OS: Windows 11 Pro (10.0.22621)
  • Shell: PowerShell 5.1
  • Claude Code: 2.1.126
  • Plugin: claude-plugins-official/telegram v0.0.6
  • Bun: 1.3.13 (on PATH)
  • Tested in: both VS Code extension and claude CLI — same behavior

Summary

The Telegram plugin's MCP server connects fine and outbound replies work, but inbound Telegram DMs are never injected into the Claude Code conversation as <channel source="telegram"> blocks. Pairing-mode replies from the server (ctx.reply("Pairing required …")) also do not reach the user, suggesting the issue may extend beyond just notification injection.

What works

  1. Bot polling: ~/.claude/channels/telegram/bot.pid is populated; bun server.ts child is alive; manual launch logs telegram channel: polling as @<bot>.
  2. MCP transport: /mcp reports telegram as connected in both VS Code and CLI.
  3. Bot receives DMs: Telegram shows the bot''s "typing…" indicator briefly when an allowlisted user DMs — proves handleInbound runs (bot.api.sendChatAction(chat_id, "typing") at server.ts:946).
  4. Outbound MCP tool calls work: calling mcp__plugin_telegram_telegram__reply with the user''s chat_id successfully delivers a message (verified — message ID returned, user received it).
  5. Bot commands work: /start triggers the welcome reply from bot.command("start") at server.ts:684.

What doesn''t work

  • Inbound DMs are never injected into the Claude Code conversation as <channel source="telegram"> blocks. The mcp.notification({ method: "notifications/claude/channel", params: {...} }) call at server.ts:963 fires (it''s downstream of the typing indicator we observed), but Claude Code never surfaces the message in the user''s conversation context.
  • Pairing-mode replies don''t reach the user: in dmPolicy: "pairing", when a non-allowlisted sender DMs, handleInbound should call ctx.reply("Pairing required — run in Claude Code: /telegram:access pair <code>") at server.ts:912. The user only sees the bot''s typing indicator vanish; no pairing-code message arrives.
  • Permission-style replies (y xxxxx / n xxxxx) similarly produce no observable effect.

Steps to reproduce

Setup:

  1. On Windows 11, install bun: powershell -c "irm bun.sh/install.ps1 | iex"
  2. Restart shell so bun is on PATH; verify bun --version
  3. Install the official Telegram plugin (lands at ~/.claude/plugins/cache/claude-plugins-official/telegram/0.0.6/)
  4. Run /telegram:configure <BotFather token>
  5. Restart VS Code from a fresh PowerShell so the MCP child inherits the bun-aware PATH
  6. Verify /mcp shows telegram as connected
  7. Run /telegram:access policy allowlist and /telegram:access allow <your-telegram-user-id> (get ID from @userinfobot)

Reproduce:

  1. From the allowlisted Telegram account, DM the bot with any plain text (e.g. hello)
  2. Observe Telegram briefly shows the bot''s "typing…" indicator, then disappears with no reply
  3. In Claude Code, send any prompt (e.g. did my message arrive?)
  4. Expected: prompt contains <channel source="telegram" chat_id="..." message_id="..." user="..." ts="...">hello</channel>
  5. Actual: no <channel> block ever appears

Confirm outbound (rules out the bot):

  • Invoke mcp__plugin_telegram_telegram__reply with chat_id = user''s Telegram ID and any text — user receives the message; tool returns a message ID. Outbound is fully functional.

Diagnostic data

  • Get-CimInstance Win32_Process -Filter "Name=''bun.exe''" shows two healthy bun processes:
  • parent wrapper (bun run --cwd ... --shell=bun --silent start)
  • child (bun.exe server.ts) — PID matches ~/.claude/channels/telegram/bot.pid
  • No competing/zombie pollers (no 409 Conflict in stderr)
  • ~/.claude/channels/telegram/inbox/ is empty (expected for text-only DMs — server only writes inbox files for media)
  • /mcp reconnect did not change behavior
  • Reproduces in both VS Code extension and a fresh claude CLI session started from the bun-aware PowerShell

Hypothesis

Claude Code 2.1.126 is not registering / not handling the custom MCP notification methods used by this plugin:

  • notifications/claude/channel (inbound DM forwarding, server.ts:963)
  • notifications/claude/channel/permission (permission-reply intercept, server.ts:929)

The MCP transport itself is healthy — tools/list and tools/call both work, as proven by outbound replies. The notification handler on the Claude Code side appears to be dropping or not subscribing to these custom methods.

Workaround

None within the plugin. Outbound replies still function (Claude can push messages to the user''s Telegram), but the user cannot reach Claude through Telegram.
'@

LozzKappa · 2 months ago

For anyone hitting the silent inbound notification bug (v2.1.x), I've documented a production-tested blueprint/workaround that ensures session persistence and reliable message delivery on Linux/Raspberry Pi.
​It bypasses the MCP notification drops by using a file-based inbox and tmux send-keys for input injection, maintaining a "sane" session state even after the first reply. Tested on RPi 4 / Debian.
​Complete Blueprint & Code: https://github.com/LozzKappa/claude-code-telegram-bot

tjhucka · 1 month ago

Reposting with fresh evidence as of 2026-06-01.

We're hitting the same polling degradation on claude 2.1.114, the version we pinned specifically to avoid the 2.1.126 regression. Different timeline -- it manifests after 24-48 hours of session age rather than immediately -- but the same end state.

Repro:

Start a claude session with --channels plugin:telegram@claude-plugins-official on a pinned 2.1.114.

Inbound Telegram delivery works normally for the first 24h.

Leave the session running ~48 hours.

Plugin status line continues showing "Listening for channel messages". No error, no disconnect indicator.

Inbound Telegram messages stop being delivered to the session.

External monitoring (Telegram API reachability, tmux liveness, plugin status string) all report green.

Only working remediation is tmux kill-session to force a fresh claude process. The new session polls correctly for another 24-48h, then the cycle repeats.

Behavior is consistent across two separate bot instances on the same machine (each with its own TELEGRAM_STATE_DIR and bot token), so it isn't bot-specific.

Note: my variant may be subtly different from the main thread here. The reports here describe the plugin polling Telegram successfully but inbound messages not reaching the session. What I'm seeing on 2.1.114 looks like the plugin reports "connected" but never actually polls the Bot API at all -- no outbound TCP to api.telegram.org, getUpdates accumulates unconsumed messages. Could be the same root cause surfacing two ways, could be distinct. Flagging in case it helps maintainers triage.

Workaround in place is a scheduled nightly kill-session. Would appreciate confirmation this is on someone's radar, or pointers to a config flag we're missing.

The-Ladder-of-Rrogress · 1 month ago

Workaround: claude -p per-message bridge

The root cause is confirmed: CC host does not declare experimental.claude/channel in MCP client capabilities, so all inbound notifications are silently dropped (#64470).

Working solution: Independent bridge script using claude -p (Architecture A), bypassing the broken MCP channel entirely.

Telegram (long polling) → grammY bot → claude -p → Telegram reply

Quick start

# In a separate terminal
cd .telegram-bridge
bun install
TELEGRAM_BOT_TOKEN=<your-token> bun run bridge.ts

Key code pattern

import { spawn } from "child_process";

function runClaude(prompt: string, sessionId?: string): Promise<string> {
  return new Promise((resolve, reject) => {
    const args = ["-p", "--dangerously-skip-permissions"];
    if (sessionId) args.push("--resume", sessionId);
    args.push(prompt);

    const child = spawn("claude", args, { stdio: ["pipe", "pipe", "pipe"] });
    let stdout = "";
    child.stdout.on("data", (d) => (stdout += d.toString()));
    child.on("close", () => resolve(stdout.trim()));
    child.on("error", reject);
  });
}

Limitations

  • Single CC instance (each message spawns a new process)
  • No streaming (waits for full response)
  • Session context via --resume <session-id>

Related repos

Tested on Windows 11, Claude Code 2.1.161.

james-cross · 21 days ago

Confirming on Claude Max (macOS, Bun runtime, Claude Code 2.1.190 and 2.1.191). Outbound works (the reply tool sends fine); inbound notifications/claude/channel never reach the session. This matches the tengu_harbor root-cause report consolidated here from #46299, and the non-deterministic registration described above.

Two extra data points from this setup:

  1. The telegram plugin's local stdio server does not start at all when loaded as a plugin (confirmed via claude mcp list; only remote plugin servers such as vercel appear). So the plugin channel is unusable here, in addition to the notification-delivery problem.
  1. Defining the same server manually as a server: entry and launching with --dangerously-load-development-channels does start it, but inbound then lands in the TUI prompt buffer instead of starting a turn. That specific failure is tracked separately in #61010.

One clean instance of "worked for months, broke with no changes": the channel registered fine until a reboot, after which fresh sessions consistently log Channel notifications skipped.

localden collaborator · 21 days ago

Thank you for taking the time to report this.

We're currently triaging open MCP issues, and this one is being closed in favor of tracking it in #36431, which covers the host failing to negotiate the experimental.claude/channel capability during initialization, resulting in channel notifications never being delivered to the plugin runtime. Please follow that issue for updates and feel free to add any additional context there.