Sandbox
@Blackman99/agent-feishu-channel

Feishu bot for Claude Code and Codex

This repo connects Claude Code and Codex to Feishu/Lark so you can chat with an agent in a group thread. It includes provider adapters, slash commands, approval cards, persistence, and runtime config so sessions keep working across restarts.

48 stars5 forksTypeScriptUpdated 6d ago
Who it's for

Builders who want to run coding agents inside Feishu group chat.

What it delivers

You can start, pause, resume, and approve agent work from Feishu without leaving the conversation.

What it does

Dual provider support

Switch between Claude and Codex per config or per session.

Session persistence

Keeps chat state on disk and resumes conversations after restarts.

Permission brokering

Turns tool calls into approval cards in Feishu before the agent acts.

Slash commands

Supports commands like `/new`, `/resume`, `/cd`, `/provider`, and `/config set`.

Queue and interrupt

Queues incoming chat while the agent is working and lets `!` interrupt the current turn.

Runtime config

Lets you change selected settings from chat without restarting the service.

How to get it

  1. 1Run
    npm install -g agent-feishu-channel
  2. 2Run
    afc init
    # Creates ~/.agent-feishu-channel/config.toml from template
  3. 3Edit the config with your Feishu credentials
    vim ~/.agent-feishu-channel/config.toml
  4. 4Run
    afc
  5. 5Run
    afc [options]            Start the service
    afc init                 Create config template at ~/.agent-feishu-channel/config.toml
    
    Options:
      -c, --config <path>    Path to config.toml (overrides default location)
      -v, --version          Show version number
      -h, --help             Show help

README

AFC Logo

agent-feishu-channel

Claude and Codex, natively in Feishu / Lark.
A full coding-agent workflow — right inside your Feishu group chat.

npm version npm downloads CI node version

English | 中文

Migrating from claude-feishu-channel? The project was renamed to reflect multi-provider support (Claude + Codex). Run pnpm remove claude-feishu-channel && pnpm add agent-feishu-channel (or the npm equivalent). Command is now afc instead of cfc. On first run, the state directory at ~/.claude-feishu-channel/ will be auto-renamed to ~/.agent-feishu-channel/ — session history is preserved. Config keys are unchanged.

Features

  • Dual providers — switch between Claude and Codex per config or per session
  • Full coding agent — file editing, shell commands, search, planning
  • Permission brokering — tool calls post interactive approval cards in Feishu
  • Session persistence — survives process restarts, auto-resumes conversations
  • Queue & interrupt — messages queue during generation; ! prefix interrupts
  • Interactive cards — streaming status, tool activity, thinking blocks, permissions
  • Staged context mitigation — warn, then hard 50MB fallback
  • Runtime config/config set to tune behavior without restart

Quick Start

Install

npm install -g agent-feishu-channel

Initialize config

afc init
# Creates ~/.agent-feishu-channel/config.toml from template

Edit the config with your Feishu credentials:

vim ~/.agent-feishu-channel/config.toml

To discover your Feishu open_id on first run, temporarily set allowed_open_ids = [] and unauthorized_behavior = "reject", then send the bot a message. It will reply with your open_id; add that value to allowed_open_ids and switch back to "ignore" for normal use.

Run

afc

The bot connects to Feishu via WebSocket and starts listening for messages.

CLI Options

afc [options]            Start the service
afc init                 Create config template at ~/.agent-feishu-channel/config.toml

Options:
  -c, --config <path>    Path to config.toml (overrides default location)
  -v, --version          Show version number
  -h, --help             Show help

Prerequisites

  • Node.js >= 20
  • Claude CLIclaude binary in $PATH when using the Claude provider
  • Codex CLI + SDKcodex binary in $PATH plus @openai/codex-sdk when using the Codex provider
  • Feishu bot app — created at open.feishu.cn

Commands

CommandDescription
/newStart a new session (clear context)
/stopInterrupt current generation
/statusShow session state, model, reasoning effort, token usage
/costShow token usage totals (input / output / total) for this session
/contextShow context window usage and mitigation status
/compactReset the current session to free context (idle-only)
/sessionsList all known sessions
/projectsList all configured project aliases
/resume <id>Resume a previous session
/cd <path>Change working directory (with confirm card)
/project <alias>Switch to a configured project alias
/provider <claude|codex>Switch the current session provider
/mode <mode>Set permission mode: default, acceptEdits, plan, bypassPermissions
/model <name>Switch the current provider model
/effort <level>Switch the current provider reasoning effort
/config showDisplay current configuration
/config set <key> <value>Change a config value at runtime
/config set <key> <value> --persistChange and write back to config.toml
/memoryShow current provider memory files (CLAUDE.md for Claude, AGENTS.md for Codex)
/memory add <text>Append <text> as a bullet to the current provider's project memory file
/helpShow available commands

Special inputs:

InputEffect
!<text>Interrupt current turn + run <text> as new turn
Plain textQueue as next turn (or start immediately if idle)

Configuration

See config.example.toml for all options with comments.

Sections

SectionKeysDescription
[feishu]app_id, app_secret, encrypt_key, verification_tokenFeishu bot credentials
[access]allowed_open_ids, unauthorized_behaviorWho can talk to the bot
[agent]default_provider, default_cwd, default_permission_mode, permission_timeout_seconds, permission_warn_before_secondsShared defaults and legacy fallbacks
[claude]default_permission_mode, default_model, default_effort, permission_timeout_seconds, permission_warn_before_seconds, cli_pathClaude provider defaults
[codex]default_permission_mode, default_model, default_effort, cli_pathCodex provider defaults
[render]inline_max_bytes, hide_thinking, show_turn_statsCard rendering options
[persistence]state_file, log_dir, session_ttl_daysState and log paths
[logging]levelLog level: trace, debug, info, warn, error
[projects]<alias> = "<path>"Project aliases for /project command
[[mcp]] (array)name, type (stdio/sse), command/args/env or urlCustom MCP servers exposed to the active provider

Runtime-settable keys

These keys can be changed via /config set without restart:

render.hide_thinking, render.show_turn_stats, render.inline_max_bytes, logging.level, agent.default_provider, agent.default_cwd, agent.default_permission_mode, agent.permission_timeout_seconds, agent.permission_warn_before_seconds, claude.default_model, claude.default_effort, claude.default_permission_mode, claude.permission_timeout_seconds, claude.permission_warn_before_seconds, codex.default_model, codex.default_effort, codex.default_permission_mode

Upgrading old configs

Existing Claude-only configs continue to load. Legacy [claude] values are used as shared fallbacks when [agent] is absent or only partially present, and Codex receives safe defaults (gpt-5.5, high effort, shared permission mode). Users can move to the new layout gradually with /config set ... --persist; no one-time manual migration is required.

Architecture

Feishu WebSocket
      │
      ▼
FeishuGateway (event decryption, dedup, access control)
      │
      ├─ onMessage ──▶ parseInput (router)
      │                    │
      │                    ├─ /command ──▶ CommandDispatcher
      │                    │
      │                    └─ plain text ──▶ ClaudeSession.submit
      │                                        │
      │                                        ▼
      │                           provider queryFn (Claude or Codex)
      │                                        │
      │                                        ├─ tool_use ──▶ PermissionBroker ──▶ Feishu card
      │                                        ├─ thinking ──▶ Feishu card (streaming)
      │                                        └─ text ──▶ Feishu answer card
      │
      └─ onCardAction ──▶ PermissionBroker.resolveByCard
                          QuestionBroker.resolveByCard
                          CommandDispatcher.resolveCdConfirm

Key components:

  • FeishuGateway — receives WebSocket events, verifies signatures, deduplicates, enforces access control
  • ClaudeSession — shared session state machine (idle → generating → idle) with message queue, drives the selected provider runtime
  • ClaudeSessionManagerchat_id → ClaudeSession map with persistence, provider selection, and crash recovery
  • FeishuPermissionBroker — posts permission cards, tracks pending approvals, handles timeouts
  • CommandDispatcher — handles slash commands (/new, /cd, /config set, etc.)

Context Handling

The bot now applies staged mitigation before it hits Claude's 50MB hard request limit:

  1. warn — notify that the session is getting large
  2. hard reset fallback — keep the backend-driven Request too large / max 50MB reset-and-retry path as the last fallback

Use /context to inspect current window usage and see the mitigation order reflected in user-facing output.

Development

# Clone and install
git clone https://github.com/Blackman99/agent-feishu-channel.git
cd agent-feishu-channel
pnpm install

# Run in dev mode
pnpm dev

# Run tests
pnpm test

# Type check
pnpm typecheck

# Build
pnpm build

Environment Variables

VariableDescription
AGENT_FEISHU_CONFIGOverride config file path (default: ~/.agent-feishu-channel/config.toml)
CLAUDE_FEISHU_CONFIGLegacy alias for AGENT_FEISHU_CONFIG (still honored)
ANTHROPIC_BASE_URLCustom API endpoint for Claude SDK
ANTHROPIC_AUTH_TOKENAuth token for custom endpoint

Current Codex Limits

  • Mid-turn acceptEdits escalation is still a provider-specific downgrade on Codex: setPermissionMode() is a safe no-op in the current adapter.

License

MIT

Files in the repo

Repository payload17 top-level entries
  • .claude
  • .github
  • assets
  • docs
  • site
  • src
  • test
  • .gitignore
  • config.example.toml
  • LICENSE
  • package.json
  • pnpm-lock.yaml
  • README.md
  • README.zh.md
  • tsconfig.build.json
  • tsconfig.json
  • vitest.config.ts

Discussion (0)

Ask about usage, or say what you built with it

Sign in to join the discussion.

No comments yet. Be the first to say what this is good for.

More connectors

Real-time global intelligence dashboard. AI-powered news aggregation, geopolitical monitoring, and infrastructure tracking in a unified situational awareness interface

86k

High-performance code intelligence MCP server. Indexes codebases into a persistent knowledge graph — average repo in milliseconds. 158 languages, sub-ms queries, 99% fewer tokens. Single static binary, zero dependencies.

43k

Universal provider proxy for OpenAI Codex & Claude Code — use any LLM (Claude, Gemini, Grok, DeepSeek, Ollama…) with Codex CLI, App, SDK, and Claude Code

14k
okf-memory/
okf-agent-memory

Git-native persistent memory for AI coding agents. Implements Google OKF v0.2 with sub-300µs in-memory BM25 search, embedded MCP server, and progressive disclosure. Slashes token bloat by 80% with zero external databases or dependencies. Built in pure Go.

547
tirth8205/
code-review-graph

Local-first code intelligence graph for MCP and CLI. Builds a persistent map of your codebase so AI coding tools read only what matters, with benchmarked context reductions on reviews and large-repo workflows.

31k
2akouwu/
reverify

Stop your AI from making things up — it proposes, deterministic tools decide, every claim checked against ground truth with evidence. Grounded facts and context survive resets. Reverse engineering is the proving ground. MCP server + CLI.

1.1k